Apa pro dan kontra dunia nyata dari menjalankan perintah SQL dinamis dalam prosedur tersimpan di SQL Server menggunakan
EXEC (@SQL)
melawan
EXEC SP_EXECUTESQL @SQL
?
Jawaban:
sp_executesql
lebih cenderung mempromosikan penggunaan kembali rencana kueri. Saat menggunakan sp_executesql
, parameter secara eksplisit diidentifikasi dalam tanda tangan panggilan. Artikel yang sangat bagus ini menjelaskan proses ini .
Referensi yang sering dikutip untuk banyak aspek sql dinamis adalah Erland Sommarskog's harus membaca: " The Curse and Blessings of Dynamic SQL ".
Hal besar tentang SP_EXECUTESQL adalah memungkinkan Anda membuat kueri berparameter yang sangat baik jika Anda peduli dengan injeksi SQL.
Artikel Microsoft's Using sp_executesql merekomendasikan penggunaan sp_executesql
alih-alih execute
pernyataan.
Karena prosedur tersimpan ini mendukung substitusi parameter , sp_executesql lebih fleksibel daripada EXECUTE; dan karena sp_executesql menghasilkan rencana eksekusi yang kemungkinan besar akan digunakan kembali oleh SQL Server, sp_executesql lebih efisien daripada EXECUTE.
Jadi, take away: Jangan gunakan execute
pernyataan . Gunakan sp_executesql
.
sp_executesql
tidak dapat digunakan untuk menggantikan execute
. Mungkin saya harus menempatkan poin yang saya coba tekankan sebagai: Gunakan sp_executesql
alih-alih execute
bila memungkinkan .
Saya akan selalu menggunakan sp_executesql hari ini, semua itu sebenarnya adalah pembungkus untuk EXEC yang menangani parameter & variabel.
Namun jangan lupa tentang OPSI RECOMPILE saat menyelaraskan kueri pada database yang sangat besar, terutama jika Anda memiliki data yang tersebar di lebih dari satu database dan menggunakan CONSTRAINT untuk membatasi pemindaian indeks.
Kecuali Anda menggunakan OPTION RECOMPILE, SQL server akan mencoba membuat rencana eksekusi "satu ukuran cocok untuk semua" untuk kueri Anda, dan akan menjalankan pemindaian indeks penuh setiap kali dijalankan.
Ini jauh lebih tidak efisien daripada seek, dan artinya ini berpotensi memindai seluruh indeks yang dibatasi ke rentang yang bahkan tidak Anda tanyakan: @
jalankan perintahnya
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
dalam SQL dinamis. Perhatikan bahwa @sql dideklarasikan sebagai varchar
ataunvarchar