#sql #sql-server #tsql #csv
#sql #sql-сервер #tsql #csv
Вопрос:
У меня есть следующий оператор Sql Server 2016 SELECT, который возвращает только 1 строку:
SELECT TOP 1 * FROM tempdb.dbo.IMTD
Как я могу объединить значения в виде строки, разделенной запятыми? ПРИМЕЧАНИЕ: имена столбцов этой временной таблицы неизвестны, поскольку они могут меняться.
Спасибо.
Комментарии:
1. Как вы выполняете этот запрос? SSMS? Powershell? Ваше собственное приложение?
2. @alroc Я использую SSMS
Ответ №1:
Возможно, что-то вроде этого:
-- Sample data
DECLARE @someTable TABLE (SomeID int identity, SomeTxt varchar(100));
INSERT @someTable VALUES ('row1'),('row2'),('row3');
-- Solution
SELECT ConcatinatedString =
STUFF
((
SELECT ',' SomeTxt
FROM @someTable
FOR XML PATH(''), TYPE
).value('.','varchar(100)'),1,1,'');
Комментарии:
1. Не могли бы вы, пожалуйста, указать, что такое «SomeTxt», у меня нет никакой информации об именах столбцов во временной таблице?
Ответ №2:
Вы можете использовать динамический запрос, как показано ниже:
DECLARE @COLS VARCHAR(MAX) = ''
SELECT @COLS = @COLS ',' COLUMN_NAME
FROM tempdb.INFORMATION_SCHEMA.COLUMNS
WHERE TABLE_NAME LIKE '#table[_]%' -- Dynamic Table (here, Temporary table)
DECLARE @COLNAMES VARCHAR(MAX) = REPLACE(STUFF(@COLS, 1, 1, ''), ',', ' '','' ')
Declare @cmd varchar(max) = 'Select ' @COLNAMES ' as CSVCol from #table'
-- will generate
-- Select Column1 ',' Column2 ',' Column3 as CSVCol from #table
EXEC (@cmd)
Комментарии:
1. Странно, @COLUMNNAMES усекается до 256 символов (но код должен работать правильно). Есть предложения? Спасибо!
2. Я думаю, это может быть связано с типом данных. Можете ли вы попробовать с
nvarchar
заменойvarchar
?3. Да, я сделал: ОБЪЯВИТЬ @COLNAMES NVARCHAR(MAX) = ЗАМЕНИТЬ (STUFF(@COLS, 1, 1, «), ‘,’, ‘ «,» ‘)
4. Какую длину вы получаете
SELECT LEN(@COLS)
?5. ВЫБЕРИТЕ len (@COLS) = 171; ВЫБЕРИТЕ LEN (@COLNAMES)=346
Ответ №3:
Другое решение, которое вы можете попробовать, это.
SELECT LTRIM(RTRIM(<ColumnName1>)) ',',
LTRIM(RTRIM(<ColumnName2>)) ',',
...
LTRIM(RTRIM(<ColumnNamen>)) ','
FROM tempdb.dbo.IMTD
Если вам нужна только одна строка, сохраните эту верхнюю 1, например
SELECT TOP 1
LTRIM(RTRIM(<ColumnName1>)) ',',
LTRIM(RTRIM(<ColumnName2>)) ',',
...
LTRIM(RTRIM(<ColumnNamen>)) ','
FROM tempdb.dbo.IMTD
LTRIM и RTRIM удалят все пробелы, и это должно позволить вам скопировать и вставить результирующий набор везде, где он может вам понадобиться. Вам нужно будет сделать это для каждого имени столбца.
Комментарии:
1. Я попробовал оба запроса, я получаю: неправильный синтаксис рядом с ‘*’.
2. @M.R. извините, я забыл, что вы должны указать имя каждого столбца, как в редактировании выше.
Ответ №4:
Вы можете использовать приведенный ниже запрос, чтобы получить имена столбцов из вашей временной таблицы.
DECLARE @ColumnNames NVARCHAR(MAX)
SELECT
@ColumnNames= COALESCE(@ColumnNames ',','') COLUMN_NAME
FROM
TempDB.INFORMATION_SCHEMA.COLUMNS
WHERE
TABLE_NAME = '#TempTableName'
Комментарии:
1. Я вижу… Я думал, что смогу избежать этого, это становится сложным… Спасибо за предложение.