Что происходит в этом коде T-SQL? (Конкатенация результатов оператора SELECT) - PullRequest
4 голосов
/ 31 марта 2010

Я только начинаю изучать T-SQL и могу использовать некоторую помощь в понимании того, что происходит в конкретном блоке кода. Я изменил некоторый код в ответе, который получил в предыдущем вопросе , и вот код, о котором идет речь:

DECLARE @column_list AS varchar(max) 
SELECT @column_list = COALESCE(@column_list, ',') + 
    'SUM(Case When Sku2=' + CONVERT(varchar, Sku2) + 
    ' Then Quantity Else 0 End) As [' + 
    CONVERT(varchar, Sku2) + ' - ' + 
    Convert(varchar,Description) +'],'
FROM OrderDetailDeliveryReview 
Inner Join InvMast on SKU2 = SKU and LocationTypeID=4
GROUP BY Sku2 , Description
ORDER BY Sku2 

Set @column_list = Left(@column_list,Len(@column_list)-1)

Select @column_list

----------------------------------------

1 row is returned:
,SUM(Case When Sku2=157 Then Quantity Else 0 End) As [157 -..., SUM(Case ...

Код T-SQL делает именно то, что я хочу, а именно, чтобы получить один результат на основе результатов запроса, который затем будет использован в другом запросе.

Однако я не могу понять, как оператор SELECT @column_list =... помещает несколько значений в одну строку символов, находясь внутри оператора SELECT. Без присваивания @column_list оператор SELECT просто вернет несколько строк. Как получается, что наличие переменной в операторе SELECT приводит к тому, что результаты сводятся в одно значение? Как мне прочитать этот T-SQL, чтобы правильно понять, что происходит?

Ответы [ 2 ]

3 голосов
/ 31 марта 2010

В SQL Server:

SELECT @var = @var + col
FROM TABLE

на самом деле объединяет значения. Это режим причуд (и в настоящее время я не могу найти ссылку на документацию функции, которая уже много лет используется в сообществе SQL Server). Если @var имеет значение NULL в начале (то есть неинициализированное значение), то вам нужен COALESCE или ISNULL (и вы часто будете использовать разделитель):

SELECT @var = ISNULL(@var, '') + col + '|'
FROM TABLE

или это сделать список, разделенный запятыми, а затем удалить только начальную запятую:

SELECT @var = ISNULL(@var, '') + ',' + col
FROM TABLE

SET @var = STUFF(@var, 1, 1, '')

или (любезно предоставлено KM , полагаясь на NULL + ',' получая NULL, чтобы исключить необходимость в STUFF для первого элемента в списке):

SELECT @var = ISNULL(@var + ',', '') + col
FROM TABLE 

или это сделать список с начальной, разделенной и завершающей запятой:

SELECT @var = ISNULL(@var, ',') + col + ','
FROM TABLE
1 голос
/ 31 марта 2010

Вы захотите заглянуть в функцию COALESCE. Хорошую статью, описывающую происходящее, можно увидеть здесь .

...