Quando il motore di query vede questo...
(SELECT TOP 1 [val] FROM @randomStuff ORDER BY NEWID())
... è tutto come "ooooh, un subquery scalare memorizzabile nella cache, lo memorizzerò nella cache!"
Devi indurre il motore di query a pensare che non sia memorizzabile nella cache. risposta
era vicino, ma il motore di query era abbastanza intelligente da vedere la tautalogia di MyTable.MyColumn = MyTable.MyColumn
, ma non è abbastanza intelligente da vedere attraverso questo.
UPDATE MyTable
SET MyColumn = (SELECT TOP 1 val
FROM @randomStuff r
INNER JOIN MyTable _MT
ON M.Id = _MT.Id
ORDER BY NEWID())
FROM MyTable M
Introducendo la tabella esterna (MT) nella sottoquery, il motore di query presuppone che la sottoquery dovrà essere rivalutata. Qualsiasi cosa funzionerà davvero, ma sono andato con la (presunta) chiave primaria di MyTable.Id poiché sarebbe stata indicizzata e avrebbe aggiunto pochissimo sovraccarico.
Un cursore sarebbe probabilmente altrettanto veloce, ma sicuramente non è altrettanto divertente.