SQL Server Parameter Sniffing及其改進(jìn)方法
SQL Server 在處理存儲過程的時候,為了節(jié)省編譯時間,是一次編譯,多次重用。當(dāng)?shù)谝淮芜\行時代入值產(chǎn)生的執(zhí)行計劃,不適用后續(xù)代入的參數(shù)時,就產(chǎn)生了parameter sniffing問題。 create procedure Sniff1(@i int) as SELECT count(b.SalesOrderID),sum(p.weight) from [Sale
SQL Server 在處理存儲過程的時候,為了節(jié)省編譯時間,是一次編譯,多次重用。當(dāng)?shù)谝淮芜\行時代入值產(chǎn)生的執(zhí)行計劃,不適用后續(xù)代入的參數(shù)時,就產(chǎn)生了parameter sniffing問題。
create procedure Sniff1(@i int) as SELECT count(b.SalesOrderID),sum(p.weight) from [Sales].[SalesOrderHeader] a inner join [Sales].[SalesOrderDetail] b on a.SalesOrderID = b.SalesOrderID inner join Production.Product p on b.ProductID = p.ProductID where a.SalesOrderID =@i; go DBCC FREEPROCCACHE exec Sniff1 50000; exec Sniff1 75124; go
Parameter Sniffing問題發(fā)生不頻繁,只會發(fā)生在數(shù)據(jù)分布不均勻或者代入?yún)?shù)值不均勻的情況下。現(xiàn)在,我們就來探討下如何解決這類問題。
1. 使用Exec() 方式運行動態(tài)SQL
create procedure Nosniff1(@i int) as declare @cmd varchar(1000); set @cmd = 'SELECT count(b.SalesOrderID),sum(p.weight) from [Sales].[SalesOrderHeader] a inner join [Sales].[SalesOrderDetail] b on a.SalesOrderID = b.SalesOrderID inner join Production.Product p on b.ProductID = p.ProductID where a.SalesOrderID ='; exec(@cmd+@i); go
exec Nosniff1 50000;
exec Nosniff1 75124;
從上述trace中可以看到,在執(zhí)行查詢語句之前,都有SP: CacheInsert事件,SQL Server做了動態(tài)編譯,根據(jù)變量的值,都正確的預(yù)估了結(jié)果集,給出了不同的執(zhí)行計劃。
2. 使用本地變量
create procedure Nosniff2(@i int) as declare @iin int; set @iin=@i SELECT count(b.SalesOrderID),sum(p.weight) from [Sales].[SalesOrderHeader] a inner join [Sales].[SalesOrderDetail] b on a.SalesOrderID = b.SalesOrderID inner join Production.Product p on b.ProductID = p.ProductID where a.SalesOrderID =@iin; go
exec Nosniff2 50000;
exec Nosniff2 75124;
如上一篇文章所述,使用本地變量,參數(shù)值在存儲過程語句執(zhí)行過程中得到,SQL Server在運行時不知道變量的值,會根據(jù)一個預(yù)估值進(jìn)行編譯,給出一個折中的執(zhí)行計劃。
3. 使用Query Hint,指定執(zhí)行計劃
在 SELECT、DELETE、UPDATE 和 MERGE 語句最后加上OPTION ( [ ,...n ] ),對執(zhí)行計劃進(jìn)行指導(dǎo)。當(dāng)數(shù)據(jù)庫管理員知道問題所在時,可以通過hint引導(dǎo)SQL Server生成一個對所有變量都不太差的執(zhí)行計劃。
以上所述是小編給大家介紹的SQL Server Parameter Sniffing及其改進(jìn)方法,希望對大家有所幫助,如果大家有任何疑問請給我留言,小編會及時回復(fù)大家的。在此也非常感謝大家對腳本之家網(wǎng)站的支持!
相關(guān)文章
SQL Server 數(shù)據(jù)庫實用SQL語句
本文將詳細(xì)介紹SQL Server 數(shù)據(jù)庫實用SQL語句,需要了解更多的朋友可以參考下2012-11-11在查詢結(jié)果中添加一列表示記錄的行數(shù)的sql語句
如何在查詢結(jié)果中添加一列表示記錄的行數(shù)? 要求是增加一列顯示行數(shù)2008-03-03檢測SqlServer數(shù)據(jù)庫是否能連接的小技巧
這篇文章主要介紹了檢測SqlServer數(shù)據(jù)庫是否能連接的小技巧,本文使用UDL文件的形式實現(xiàn)這個小方法,需要的朋友可以參考下2015-02-02Sql Server中的系統(tǒng)視圖詳細(xì)介紹
這篇文章主要介紹了Sql Server中的系統(tǒng)視圖詳細(xì)介紹,本文講解了系統(tǒng)視圖是干什么呢、都定義在哪呢、一些使用例子等內(nèi)容,需要的朋友可以參考下2015-02-02Sql Server 2012 轉(zhuǎn)換函數(shù)的比較(Cast、Convert和Parse)
Cast、Convert 和 Parse 都是 Sql Server 2012 中的內(nèi)置轉(zhuǎn)換函數(shù),其作用是:一種數(shù)據(jù)類型轉(zhuǎn)換為另一種數(shù)據(jù)類型。其中前兩者的差別較小,但 Parse 為 Sql Server 2012 新增函數(shù),也是最近在分析 Sql Server 2012 新特性的時間,才有想把這3個函數(shù)拿出來進(jìn)行比較分析的想法2012-07-07sqlserver查找括號()中字符串內(nèi)容的方法實現(xiàn)
本文主要介紹了sqlserver查找括號()中字符串內(nèi)容的方法實現(xiàn),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2023-05-05