2016-12-09 87 views
3

我一直盯着這個小時和幾個小時,並不能提出一個「優雅的」基於集合的方式來獲得我需要的結果集.. 。使用TSQL SQL Server有條件地選擇行(2008 R2)

這裏是我的樣本數據(我的真實數據可能是1,000,000行)...

DECLARE @t AS TABLE (ID int,ID1 nvarchar(15),[DATE] date,PERIOD int,[TYPE] nchar(1)); 

INSERT INTO @t (ID,ID1,[DATE],PERIOD,[TYPE]) 
VALUES 
(1,N'NUM1','2016-01-01',1,N'B'), 
(2,N'NUM1','2016-01-01',2,N'A'), 
(3,N'NUM1','2016-01-01',3,N'A'), 
(4,N'NUM1','2016-01-01',4,N'B'), 
(5,N'NUM1','2016-01-01',4,N'A'), 
(6,N'NUM1','2016-01-01',5,N'A'), 

(7,N'NUM1','2016-01-02',1,N'A'), 
(8,N'NUM1','2016-01-02',2,N'A'), 
(9,N'NUM1','2016-01-02',3,N'A'), 
(10,N'NUM1','2016-01-02',4,N'A'), 
(11,N'NUM1','2016-01-02',5,N'A'), 

(12,N'NUM2','2016-01-01',1,N'A'), 
(13,N'NUM2','2016-01-01',1,N'B'), 
(14,N'NUM2','2016-01-01',2,N'A'), 
(15,N'NUM2','2016-01-01',3,N'A'), 
(16,N'NUM2','2016-01-01',4,N'B'), 
(17,N'NUM2','2016-01-01',4,N'A'), 
(18,N'NUM2','2016-01-01',5,N'A'), 

(19,N'NUM2','2016-01-02',1,N'A'), 
(20,N'NUM2','2016-01-02',2,N'B'), 
(21,N'NUM2','2016-01-02',3,N'A'), 
(22,N'NUM2','2016-01-02',4,N'A'), 
(23,N'NUM2','2016-01-02',4,N'B'), 
(24,N'NUM2','2016-01-02',5,N'A'); 

下面是結果集,我試圖讓...

1,'NUM1','2016-01-01',1,'B' 
2,'NUM1','2016-01-01',2,'A' 
3,'NUM1','2016-01-01',3,'A' 
5,'NUM1','2016-01-01',4,'A' 
6,'NUM1','2016-01-01',5,'A' 

7,'NUM1','2016-01-02',1,'A' 
8,'NUM1','2016-01-02',2,'A' 
9,'NUM1','2016-01-02',3,'A' 
10,'NUM1','2016-01-02',4,'A' 
11,'NUM1','2016-01-02',5,'A' 

12,'NUM2','2016-01-01',1,'A' 
14,'NUM2','2016-01-01',2,'A' 
15,'NUM2','2016-01-01',3,'A' 
17,'NUM2','2016-01-01',4,'A' 
18,'NUM2','2016-01-01',5,'A' 

19,'NUM2','2016-01-02',1,'A' 
20,'NUM2','2016-01-02',2,'B' 
21,'NUM2','2016-01-02',3,'A' 
22,'NUM2','2016-01-02',4,'A' 
24,'NUM2','2016-01-02',5,'A' 

簡而言之,每天有5個時期。他們可以是A型或B型。我需要獲得A型。但如果沒有A類型,我需要得到B類型......(聽起來很簡單,當我把它寫出來,但我的大腦不會拿出合適的東西)

Pleeeeeease讓我走出我的痛苦..

+0

你所需的輸出不適合你的問題陳述。對於每個日期都有'A',所以沒有任何日期可以得到'B'。你的輸出應該只有'A's? –

+0

我認爲他意味着每個日期和時期 –

回答

7

您可以使用ROW_NUMBER此:

SELECT ID, ID1, [DATE], PERIOD, [TYPE] 
FROM (
    SELECT ID, ID1, [DATE], PERIOD, [TYPE], 
      ROW_NUMBER() OVER (PARTITION BY ID1, [DATE], PERIOD 
          ORDER BY [TYPE]) AS rn 
    FROM @t) AS t 
WHERE t.rn = 1 

ROW_NUMBER地方'A'記錄OVER子句中頂'B'記錄使用ORDER BY [TYPE]。如果對於給定的ID1, [DATE], PERIOD沒有'A'記錄,則B記錄被分配爲rn = 1

+0

這可能是最快的給定解決方案 –

0

您希望的outpout與「我需要獲得A類型但是如果沒有A類型,我需要獲得B類型...」的說法相矛盾。數據中的每個日期都有一個或多個'A'類型。通過聲明,輸出應該只包含'A'類型。但是,如果該語句是正確的,那麼這應該工作:

Select d.[DATE], t.Id, t.ID1, t.PERIOD, t.[TYPE] 
from (select distinct [date] from @t) d 
    left join @t t 
    on t.[date] = d.[date] 
    and t.type = case when exists 
     (select * from @t 
     where [date] = d.[Date] 
      and type = 'A') then 'A' 
      else 'B' End 
0

我剛剛想出

SELECT * FROM @t WHERE [TYPE]='A' 
    UNION ALL 
    SELECT * FROM @t t1 WHERE [TYPE]='B' AND NOT EXISTS (SELECT ID FROM @t WHERE ID1=t1.ID1 AND [TYPE]='A' AND [DATE]=t1.[DATE] AND Period=t1.Period) 
ORDER BY ID; 

這給的我什麼,我需要......