2012-04-23 109 views
1

選擇最新的記錄組我有這個數據表:通過用戶名在SQL Server 2008

ID voting_ID username timestamp    XMLBallot 
1 9   voter01 23. 4. 2012 8:54:45 xmldata 
2 9   voter01 21. 4. 2012 14:00:34 xmldata 
3 9   voter02 20. 4. 2012 16:01:10 xmldata 
4 11   voter01 23. 4. 2012 8:40:45 xmldata 
5 9   voter03 19. 4. 2012 21:18:49 xmldata 

我需要一個只在特定voting_ID每個選民(用戶名)最新的選票。

數據。舉例來說,我需要​​

ID voting_ID username timestamp    XMLBallot 
1 9   voter01 23. 4. 2012 8:54:45 xmldata 
3 9   voter02 20. 4. 2012 16:01:10 xmldata 
5 9   voter03 19. 4. 2012 21:18:49 xmldata 

退換請幫我建立一個SQL Server 2008中查詢。謝謝 PS:表名是​​

回答

5

您有幾種選擇這裏但使用添加一個ROW_NUMBER分組user和排序(降序)在您的timestamp允許您輕鬆選擇最新的記錄。

使用ROW_NUMBER

SELECT * 
FROM (
     SELECT ID, voting_ID, username, timestamp, XMLBallot 
       , rn = ROW_NUMBER() OVER (PARTITION BY voting_ID, username ORDER BY timestamp DESC) 
     FROM Ballots 
     ) bt 
WHERE rn = 1 

或者,您也可以選擇每個用戶的最大時間戳和加入上。

使用MAX

SELECT bt.ID, bt.voting_ID, bt.username, bt.timestamp, bt.XMLBallot 
FROM Ballots bt 
     INNER JOIN (
      SELECT username, voting_ID, timestamp = MAX(timestamp) 
      FROM Ballots 
      GROUP BY 
       username, voting_ID 
     ) btm ON btm.username = bt.Username 
       AND btm.voting_ID = bt.voting_ID 
       AND btm.timestamp = bt.timestamp 
+1

好像'集團BY'從您的替代解決方案的'INNER JOIN'失蹤。 – 2012-04-23 08:45:11

+0

@AzizShaikh - thx發現...這是星期一,我能說什麼。 – 2012-04-23 08:48:33

+0

謝謝,但這不適用於其他voting_ID ..這隻選擇voting_ID = 9 ..當我試圖通過voting_ID = 11 f.ex選擇記錄。沒有任何回報.. – Gondy 2012-04-23 12:47:31

1

也許是這樣的:

測試數據

DECLARE @T TABLE 
    (
     ID INT, 
     voting_ID int, 
     username VARCHAR(100), 
     timestamp VARCHAR(100), 
     XMLBallot VARCHAR(100) 
    ) 

INSERT INTO @T 
VALUES 
    (1,9,'voter01','23. 4. 2012 8:54:45','xmldata'), 
    (2,9,'voter01','21. 4. 2012 14:00:34','xmldata'), 
    (3,9,'voter02','20. 4. 2012 16:01:10','xmldata'), 
    (4,11,'voter01','23. 4. 2012 8:40:45','xmldata'), 
    (5,9,'voter03','19. 4. 2012 21:18:49','xmldata') 

查詢

DECLARE @voting_ID INT=9 
;WITH CTE 
AS 
( 
    SELECT 
     ROW_NUMBER() OVER(PARTITION BY username ORDER BY voting_ID) AS RowNbr, 
     t.* 
    FROM 
     @T AS t 
) 
SELECT 
    * 
FROM 
    CTE 
WHERE 
    RowNbr=1 
    AND [email protected]_ID 

EDIT1

也許是這樣,那麼:

DECLARE @voting_ID INT=9 
;WITH CTE 
AS 
( 
    SELECT 
     ROW_NUMBER() OVER(PARTITION BY username ORDER BY timestamp DESC) AS RowNbr, 
     t.* 
    FROM 
     @T AS t 
    WHERE 
     [email protected]_ID 
) 
SELECT 
    * 
FROM 
    CTE 
WHERE 
    RowNbr=1 
+0

而我可以通過voting_ID參數?我只需要從特定投票中選擇選票 – Gondy 2012-04-23 08:46:42

+0

@Gondy - 您可以將其添加到where子句中,成爲'Where RowNbr = 1 AND voting_ID = @ Voting_ID' – 2012-04-23 08:49:48

+0

已更新答案 – Arion 2012-04-23 09:22:55

-1
select t1_4.ID, t1_4.voting_id, t1_4.timestamp, t1_4.xmlballot 
from table1 as t1_4 
where t1_4.ID in ( SELECT id_to_select 
      from ( SELECT ( SELECT t1_1.ID 
         from table1 as t1_1 
         where t1_1.id = ( SELECT top 1 t1_2.ID 
            from  table1 as t1_2 
            where t1_2.username = t1_3.username 
            order by timestamp desc) 
        ) as id_to_select, 
         t1_3.username 
        from table1 as t1_3 
        group by username) 
     ) 
1

替代辦法做到這一點。

WITH sub 
    AS (SELECT *, 
       Max(timestamp) OVER (partition BY company) AS latest 
     FROM ballots) 
SELECT * 
FROM sub 
WHERE latest = timestamp 
+0

這是一個很酷的把戲 – 2015-07-19 14:26:31