Похоже, что скорость выполнения T-SQL зависит от задержки сетевого соединения с сервером. Я предположил, что если SQL Server не будет о чем сообщить клиенту, он просто будет выполняться до тех пор, пока это не будет сделано, но тестирование покажет другую историю.
create procedure UselessLoop
@I int
as
declare @D datetime = getdate()
while @I > 0 set @I -= 1
print datediff(millisecond, @D, getdate())
exec UselessLoop 100000
Server Milliseconds
local 53
nearby 63
faraway 660
exec UselessLoop 1000000
Server Milliseconds
local 546
nearby 640
faraway 6183
Тесты выполняются на одном и том же сервере с разных компьютеров с использованием SSMS. Локальный выполняется с сервера, рядом находится в той же локальной сети, а удаленный выполняется из другого офиса в 500 км, соединенного с 1 гигабитным волокном.
Очевидно, что между SQL Server и клиентом происходит некоторая связь, которая напрямую зависит от количества выполненных операторов.
Я использовал Wireshark, чтобы посмотреть на то, что транспортируется, и я не могу сказать, что я это понимаю, но это был tcp.stream, который обменивался в общей сложности 26 МБ в 22740 пакетах.
Как насчет бесполезной функции вместо этого?
create function dbo.UDFUselessLoop(@I int)
returns int
as
begin
declare @D datetime = getdate()
while @I > 0 set @I -= 1
return datediff(millisecond, @D, getdate())
end
print dbo.UDFUselessLoop(1000000)
Он выполняется за 406 миллисекунд независимо от того, откуда он выполняется. Похоже, что нет связи с клиентом в цикле.