2016-09-08 4 views
0

Я довольно смутно знаком с SQL.Как я могу группировать таблицу ObjectId?

Я использую Sql Server 2012.

У меня есть эта таблица:

|Id | SiteId| IsNormal|  DateReview   | ObjectId |FrequencyId|InspectionId | 
|3379|  5| 1  | 2016-09-08 00:00:00.000| 1019 |  1  |  16  | 
|3380|  5| 1  | 2016-09-08 00:00:00.000| 1019 |  1  |  20  | 
|3381|  5| 0  | 2016-09-08 00:00:00.000| 1020 |  1  |  16  | 
|3382|  5| 1  | 2016-09-08 00:00:00.000| 1020 |  1  |  54  | 

Мне нужно тентовых таблицу по ObjectId, если хотя бы одна строка имеет свойство ложного в таблице сгруппированы это должны быть Ложь.

Здесь желаемой сгруппированной таблице:

|Id  | SiteId| IsNormal |  DateReview   | ObjectId |FrequencyId|InspectionId | 
|3379,3380 | 5 | 1  | 2016-09-08 00:00:00.000| 1019 |  1  |  16,20 | 
|3382,3381 | 5 | 0  | 2016-09-08 00:00:00.000| 1020 |  1  |  54,16 | 

IsNormal колонка типа БИТ.

+0

почему в случае 'ObjectId = 1020' вы ожидаете' Id = 3382', а также 'IsNormal = false' ? эти данные взяты из разных строк .... не будет ли это 'Id = 3381'? – Petaflop

+0

@msanz, я обновил свой вопрос. Это была ошибка, вы могли бы это увидеть. – Michael

+0

Вы пытались решить проблему? – Tanner

ответ

2

Вы можете использовать следующие:

WITH Src AS 
(
    SELECT * FROM (VALUES 
    (3379, 5, CAST(1 AS bit), '2016-09-08 00:00:00.000', 1019, 1, 16), 
    (3380, 5, CAST(1 AS bit), '2016-09-08 00:00:00.000', 1019, 1, 20), 
    (3381, 5, CAST(0 AS bit), '2016-09-08 00:00:00.000', 1020, 1, 16), 
    (3382, 5, CAST(1 AS bit), '2016-09-08 00:00:00.000', 1020, 1, 54) 
    ) T(Id, SiteId, IsNormal, DateReview, ObjectId, FrequencyId, InspectionId) 
) 
SELECT Id, SiteId, IsNormal, DateReview, ObjectId, FrequencyId, InspectionId 
FROM 
(
    SELECT ObjectId, MIN(SiteId) SiteId, 
     CONVERT(bit, MIN(CONVERT(int, IsNormal))) IsNormal, 
     MIN(DateReview) DateReview, MIN(FrequencyId) FrequencyId 
    FROM Src 
    GROUP BY ObjectId 
) Dist 
CROSS APPLY 
(
    SELECT STUFF((SELECT ','+CONVERT(varchar(10),Id) 
    FROM Src 
    WHERE ObjectId=Dist.ObjectId 
    FOR XML PATH('')), 1, 1, '') 
) Ids(Id) 
CROSS APPLY 
(
    SELECT STUFF((SELECT ','+CONVERT(varchar(10),InspectionId) 
    FROM Src 
    WHERE ObjectId=Dist.ObjectId 
    FOR XML PATH('')), 1, 1, '') 
) InspectionIds(InspectionId) 
+0

Pawel thanks, но IsNormal coulmn бит типа – Michael

+0

Пример исправлен. –

+0

Привет Pawel.Any идея, можно ускорить запрос выше? CROSS APPLY занимает много времени. – Michael

1

Попробуйте, как это,

DECLARE @Table TABLE (
    Id INT 
    ,SiteId INT 
    ,IsNormal bit 
    ,DateReview DATETIME 
    ,ObjectId INT 
    ,FrequencyId INT 
    ,InspectionId INT 
    ) 

Insert into @Table values 
(3379,5,1, '2016-09-08 00:00:00.000',1019,1,16) 
,(3380,5,1, '2016-09-08 00:00:00.000',1019,1,20) 
,(3381,5,0,'2016-09-08 00:00:00.000',1020,1,16) 
,(3382,5,1, '2016-09-08 00:00:00.000',1020,1,54) 

SELECT STUFF((
      SELECT ',' + convert(VARCHAR(10), Id) 
      FROM @Table t 
      WHERE t.ObjectId = t1.objectid 
      FOR XML PATH('') 
      ), 1, 1, '') AS Id 
    ,siteid 
    ,CASE 
     WHEN STUFF((
        SELECT ',' + convert(VARCHAR(10), IsNormal) 
        FROM @Table t 
        WHERE t.ObjectId = t1.objectid 
        FOR XML PATH('') 
        ), 1, 1, '') LIKE '%0%' 
      THEN 0 
     ELSE 1 
     END AS IsNormal 
    ,datereview 
    ,objectid 
    ,FrequencyId 
    ,STUFF((
      SELECT ',' + convert(VARCHAR(10), InspectionId) 
      FROM @Table t 
      WHERE t.ObjectId = t1.objectid 
      FOR XML PATH('') 
      ), 1, 1, '') AS InspectionId 
FROM @Table t1 
GROUP BY siteid 
    ,datereview 
    ,objectid 
    ,FrequencyId 
+0

Благодарим за помощь. Но я допустил некоторую ошибку в моем вопросе в столбце IsNormal, если столбец бит, а не string.could вы увидите, пожалуйста, мое обновление. – Michael