Jakie są rzeczywiste wady i zalety wykonywania dynamicznego polecenia SQL w procedurze składowanej w programie SQL Server przy użyciu
EXEC (@SQL)
przeciw
EXEC SP_EXECUTESQL @SQL
?
Jakie są rzeczywiste wady i zalety wykonywania dynamicznego polecenia SQL w procedurze składowanej w programie SQL Server przy użyciu
EXEC (@SQL)
przeciw
EXEC SP_EXECUTESQL @SQL
?
Odpowiedzi:
sp_executesql
jest bardziej prawdopodobne, że będzie promować ponowne wykorzystanie planu zapytań. Podczas używania sp_executesql
parametry są wyraźnie identyfikowane w sygnaturze wywołania. Ten wspaniały artykuł opisuje ten proces .
Często cytowanym odniesieniem dla wielu aspektów dynamicznego sql jest książka Erlanda Sommarskoga, którą trzeba przeczytać: „ Klątwa i błogosławieństwa dynamicznego SQL ”.
Dużą zaletą SP_EXECUTESQL jest to, że pozwala tworzyć sparametryzowane zapytania, co jest bardzo dobre, jeśli zależy Ci na wstrzykiwaniu SQL.
Artykuł Microsoftu Using sp_executesql zaleca używanie sp_executesql
zamiast execute
instrukcji.
Ponieważ ta procedura składowana obsługuje podstawianie parametrów , sp_executesql jest bardziej wszechstronna niż EXECUTE; a ponieważ sp_executesql generuje plany wykonania, które z większym prawdopodobieństwem zostaną ponownie wykorzystane przez SQL Server, sp_executesql jest bardziej wydajne niż EXECUTE.
A więc na wynos: nie używaj execute
instrukcji . Użyj sp_executesql
.
sp_executesql
nie można ich zastąpić execute
. Być może powinienem ująć to, co staram się podkreślić, jako: Używaj sp_executesql
zamiast tego, execute
kiedy to możliwe .
W dzisiejszych czasach zawsze używałbym sp_executesql, wszystko to naprawdę jest opakowaniem dla EXEC, które obsługuje parametry i zmienne.
Jednak nie zapomnij o OPCJI RECOMPILE podczas strojenia zapytań w bardzo dużych bazach danych, zwłaszcza gdy masz dane rozłożone na więcej niż jedną bazę danych i używasz OGRANICZENIA w celu ograniczenia skanowania indeksów.
O ile nie użyjesz OPCJI RECOMPILE, serwer SQL podejmie próbę utworzenia planu wykonania zapytania „jeden rozmiar dla wszystkich” i będzie przeprowadzał pełne skanowanie indeksu przy każdym uruchomieniu.
Jest to znacznie mniej wydajne niż wyszukiwanie i oznacza, że potencjalnie skanuje całe indeksy, które są ograniczone do zakresów, których nawet nie pytasz: @
wykonać polecenie
declare @sql varchar (100)
set @sql ='select * from #td1'
if (@IsMonday+@IsTuesday !='')
begin
set @sql= @sql+' where PickupDay in ('''+@IsMonday+''','''+@IsTuesday+''' )'
end
exec( @sql)
int
w dynamicznym języku SQL. Zauważ, że @sql jest zadeklarowane jako varchar
lubnvarchar