Как объединить две таблицы и создать дополнительный столбец с разделенными запятыми значениями - PullRequest
0 голосов
/ 09 ноября 2019

У меня нет большого опыта работы с SQL, кроме запросов CRUD;пожалуйста, прости меня, если это тривиально. Я пытаюсь объединить две таблицы и создать дополнительный столбец в результатах с рядом значений, разделенных запятыми.

Таблица 1

enter image description here

Таблица 2

enter image description here

Я могу получить значения через запятую из таблицы 2, используя

DECLARE @tmp varchar(MAX)
SET @tmp = ''
SELECT @tmp = @tmp + CONVERT(VARCHAR(10), [materialTypeID])  + ', '
FROM [industryActivityMaterials] 
WHERE typeID = 1145 AND activityID =  1
SELECT SUBSTRING(@tmp, 0, LEN(@tmp)) AS materialsRequired

enter image description here

Однако я не могу понять, как объединить таблицы на typeID, чтобы получить набор результатов, содержащий столбецmaterialsReguired.

Ответы [ 3 ]

1 голос
/ 09 ноября 2019

Вы можете объединять, агрегировать и использовать функцию агрегирования string_agg() для создания списка через запятую. Эта функция доступна с SQL Server 2017.

select 
    t1.typeID, 
    t1.activityID,
    t1.activityName,
    t.Blueprint,
    t1.productTypeID,
    t1.ProductName,
    string_agg(t2.materialTypeID, ',') 
        within group (order by t2.materialTypeID) materialTypeIDs
from 
    table1 t1
    inner join table2 t2
        on  t2.typeID = t1.typeID
        and t2.activityID = t1.activityID
group by
    t1.typeID, 
    t1.activityID,
    t1.activityName,
    t.Blueprint,
    t1.productTypeID,
    t1.ProductName
0 голосов
/ 09 ноября 2019

Как примечание, независимо от подхода, вы можете найти коррелированный подзапрос более простым, чем большая агрегация:

select t1.*,
       (select string_agg(t2.materialTypeID, ',') within group (order by t2.materialTypeID)
        from table2 t2
        where t2.typeID = t1.typeID and
              t2.activityID = t1.activityID
       ) as materialTypeIds
from table1 t1;

Или:

select t1.*,
       stuff( (select concat(',', t2.materialTypeID) 
               from table2 t2
               where t2.typeID = t1.typeID and
                     t2.activityID = t1.activityID
               for xml path ('')
              ), 1, 1, ''
            ) as materialTypeIds
from table1 t1;

В целом, избегая внешней агрегацииповышает производительность, особенно если есть индекс на table2(typeID, activityId).

0 голосов
/ 09 ноября 2019

ниже версии сервера sql 2016 года вы можете использовать путь xml для группировки по строке concat

SELECT 
  T1.typeId,
  STUFF((
    SELECT ', ' + materialTypeID 
    FROM Table2 T2 
    WHERE (T2.typeId = T1.typeId) 
    FOR XML PATH(''),TYPE).value('(./text())[1]','VARCHAR(MAX)')
  ,1,2,'') AS materialsRequired
FROM Table1 T1
GROUP BY T1.typeId

поверх версии сервера sql 2016 вы можете использовать string_agg.

STRING_AGG (Transact-SQL) - SQL Server |Документы Microsoft

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...