Незвичайний потік Агрегатна поведінка


11

Запит:

declare @X xml = '
<item ID = "0"/>
<item ID = "1"/>
<item/>
<item/>';

select I.X.value('@ID', 'int')
from @X.nodes('/item') as I(X);

Результат:

-----------
0
1
NULL
NULL

План виконання:

введіть тут опис зображення

Верхня гілка розбиває XML на чотири рядки, а нижня гілка отримує значення для атрибута ID.

Що мене дивно вражає - це кількість рядків, повернених від оператора Stream Aggregate. 2 рядки, що надходять від фільтра, є IDатрибутом першого та другого itemвузлів у XML. Агрегат потоку повертає чотири рядки, по одному для кожного вхідного рядка, фактично перетворюючи Внутрішнє з'єднання на Зовнішнє з'єднання.

Це те, що Stream Aggregate робить і за інших обставин, чи це просто щось дивне, коли ви робите XML-запити?

Я не бачу жодних натяків у версії XML плану запитів про те, що ця потокова агрегація повинна вести себе інакше, ніж будь-яка інша потокова агрегата, яку я помічав раніше.

Відповіді:


13

Сукупність - скалярний сукупність (немає групи за пунктом). Вони визначені в SQL Server, щоб завжди створювати рядок, навіть якщо вхід порожній.

Наприклад, для скалярного сукупності, MAXжодних рядків не є NULL, наприклад, COUNTжодних рядків не дорівнює нулю. Оптимізатор знає все про це і може перетворити зовнішнє з'єднання у внутрішнє з'єднання за відповідних обставин.

-- NULL for a scalar aggregate
SELECT MAX(V.v) FROM (VALUES(1)) AS V (v) WHERE V.v = 2;

-- No row for a vector aggregate
SELECT MAX(V.v) FROM (VALUES(1)) AS V (v) WHERE V.v = 2 GROUP BY ();

Більш детально про агрегати читайте в моїй статті " Розваги зі скалярними та векторними агрегатами" .


10

Тут слід пам’ятати, що плани виконання висмоктують дані.

Так оператор вкладеного циклу викликає потоковий агрегат 4 рази. Агрегат потоку викликає Фільтр також 4 рази, але отримує значення лише двічі.

Таким чином, потокова сукупність дає чотири значення. Двічі він дає значення, і двічі дає Null.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.