(Soru SO'dan taşındı)
Kümelenmiş dizin 2 sütun içeren bir tablo (kukla veri) var:
Şimdi bu iki sorguyu çalıştırıyorum:
declare
@productid int =1 ,
@priceid int = 1
SELECT productid,
t.priceID
FROM Transactions AS t
WHERE (productID = @productid OR @productid IS NULL)
AND (priceid = @priceid OR @priceid IS NULL)
SELECT productid,
t.priceID
FROM Transactions AS t
WHERE (productID = @productid)
AND (priceid = @priceid)
Her iki sorgu için gerçek yürütme planı:
Gördüğünüz gibi birincisi SCAN, ikincisi SEEK kullanıyor.
Ancak - OPTION (RECOMPILE)ilk sorguyu ekleyerek , yürütme planını da SEEK kullanmak için yaptı:
DBA sohbetindeki arkadaşlar bana şunları söyledi:
Sorgunuzda @ productid = 1, yani (productID = @ productID VEYA @ productIDID IS NULL) (productID = @ productID) ile basitleştirilebilir. Birincisi, herhangi bir @productID değeri ile çalışmak için bir tarama gerektirir, ikincisi bir arama kullanabilir. Bu nedenle, RECOMPILE kullandığınızda, SQL Server @productID'de gerçekte sahip olduğunuz değere bakar ve bunun için en iyi planı yapar. @ ProducttID değerinde null olmayan bir değerle, arama en iyisidir. @ProductID değeri bilinmiyorsa, planın @productID içindeki bir tarama gerektiren herhangi bir olası değere uyması gerekir. Dikkat edin: OPTION (RECOMPILE), her çalıştırdığınızda planı yeniden derlemeye zorlar ve bu da her yürütmeye birkaç milisaniye ekler. Sorgu çok sık çalışıyorsa bu sadece bir sorundur.
Ayrıca :
@ProductID boşsa, hangi değere bakarsınız? Cevap: aranacak bir şey yok. Tüm değerler geçerlidir.
Anlıyorum OPTION (RECOMPILE)SQL Server zorlar sahiptir değerleri parametreleri gerçek olduğunu görmek ve onunla ARAMA görmek için.
Ama şimdi ön derlemenin faydasını kaybediyorum.
Soru
IMHO - SCAN yalnızca bir parametre boşsa oluşur.
Bu iyi - SQL SERVER'ın SCAN için bir yürütme planı oluşturmasına izin verin.
AMA SQL Server, bu sorguyu birçok kez değerlerle çalıştırdığımı görürse: 1,1neden başka bir yürütme planı oluşturmuyor ve bunun için SEEK kullanmıyor?
AFAIK - SQL, en çok kullanılan sorgular için yürütme planı oluşturur .
SQL SERVER neden aşağıdakiler için bir yürütme planı kaydetmiyor:
@productid int =1 , @priceid int = 1
(Bu değerlerle birçok kez çalıştırıyorum)
- SQL'i gelecekteki çağrılar için yürütme planını (SEEK kullanan) tutmaya zorlamak mümkün mü?


