2017-07-13 42 views
0

我有一個包含3列(代碼,狀態,日期)的表,它記錄了代碼狀態的歷史,每個代碼可能已多次更改狀態。表內連接本身

我要顯示的每個代碼的最後狀態我所做的就是這樣的

SELECT code,MAX(date), .... 
FROM table 
GROUP BY code. 

我不知道要放什麼東西究竟得到的狀態。我試圖只是把狀態,所以它得到的狀態對應於code,max(date)的組合,但它給了我不在集合函數中的錯誤。

非常感謝您的幫助。

+0

你可以使用一個窗口函數來做這個或者一個子查詢'select max(date),code ... group by code'然後連接。 – xQbert

+0

但是當我加入我得到多個記錄每個代碼我用一個內部聯接。 –

+0

希望我的回答涵蓋了你的問題:P – xQbert

回答

2

如果我理解你如

CODE State Date 
1  IL  1/1/2016 
1  IA  1/1/2017 
1  AL  1/1/2015 

數據,你想在你的結果

1 IA 1/1/2017 

使用窗口函數和公共表表達式(with):我們根據日期的降序爲每個代碼分配一個行號,並僅返回每個代碼的第一行。

With CTE AS (SELECT code 
      , date 
      , state 
      , Row_number() over (partition by code order by date desc) RN 
      FROM table) 
SELECT Code, Date, State 
FROM CTE 
WHERE RN =1 

使用子查詢:(我們得到每個代碼的最大日期,然後加入背部設置來限制返回的行基本

SELECT A.code, A.date, A.state 
FROM table A 
INNER JOIN (SELECT max(date) mdate, code 
      FROM table 
      GROUP BY code) B 
on A.Code = B.Code 
and A.Date = B.MDate 

後來的查詢被用來當/如果窗口。函數是不可用的解決你的問題的現代方法是使用第一種方法

實質上,第一個查詢所做的是根據日期降序爲每個代碼分配#1給x,所以最大日期得到每個代碼的RN爲1,因此當我們說RN = 1時,我們只返回代碼/狀態/記錄具有所討論的代碼的最大日期。我們使用with語句,因爲我們需要RN實現(實際上是在內存中生成的),以便我們可以在with(公用表表達式)查詢的第二部分中對其進行限制。

+0

你得到了我,這就是我想要做的。 –

1

如果您正在進行彙總,例如MAX(),那麼您選擇的所有其他非彙總列也需要在您的GROUP BY中。這就是爲什麼當您將state添加到選擇時出現錯誤。如果你把它添加到由它選擇和組,你會得到你的結果:

SELECT State, Code, MAX(Date) 
FROM table 
GROUP BY State, Code 
+0

但在這種情況下,如果我說狀態1和狀態2的代碼1,它們將是代碼2的兩倍,我需要的是每個代碼的最後狀態爲max(date)的相應狀態的唯一代碼。 –

+0

@Houss_gc我太快讀到你的問題,請檢查xQbert的回答:) –

1

如果你想用戶內部聯接就像你在帖子內你提到加入到它自身相匹配的codedate

SELECT * 
FROM table t1 
INNER JOIN (SELECT code,MAX(date) 
      FROM table 
      GROUP BY code) codeWithLatestDate ON t1.code = codeWithLatestDate.code AND t1.date = codeWithLatestDate.dat3 

不過,我會建議增加stateGROUP BY條款和SELECT cluase

SELECT code,MAX(date),state 
FROM table 
GROUP BY code, state 
+0

我會試試這個方法謝謝。 –

1

你可以用它自己加入

SELECT State,Code,Date 
FROM table t 
JOIN (
SELECT Code, MAX(Date) as Date 
FROM table 
GROUP BY Code) t1 on t1.Code= t.Code and t.Date=t1.Date