需要来自多个记录的最新行的值

时间:2019-09-24 22:00:01

标签: sql sql-server

我有以下内容:

UserID    SomeValue     DateUpdated
------------------------------------
1         263           2019-09-07
2         abc           2019-09-10
1         123           2019-09-10
2         234           2019-09-11
1         573           2019-09-20

我需要一个查询,该查询将返回不同的UserID,最新的DateUpdated值以及最新记录的相应SomeValue。

我在同一张表的子查询上尝试了外部联接。没有产生预期的结果。

SELECT B.UserID, B.SomeValue, B.DateUpdated 
FROM thetable B
LEFT OUTER JOIN 
(SELECT UserID, MAX(DateUpdated) AS DateUpdated 
 FROM thetable GROUP BY UserID) x
ON x.UserID = B.UserID AND x.DateUpdated = B.DateUpdated

但是它返回的收益比预期的要多。

从上面的数据示例中,我希望得到:

UserID    SomeValue     DateUpdated
------------------------------------
2         234           2019-09-11
1         573           2019-09-20

在生产表中,我有3,670,108条记录。外部联接返回了3,669,774,但是表中只有1,182,525个不同的用户ID。因此,我希望结果为1,182,525行。

非常感谢您的协助。

2 个答案:

答案 0 :(得分:0)

使用row_number()

select userid, somevalue, dateupdated
from (
  select *, row_number() over (partition by userid order by dateupdated desc) rn
  from thetable
) t
where rn = 1

或不存在:

select t.* from thetable t
where not exists (
  select 1 from thetable
  where userid = t.userid and dateupdated > t.dateupdated 
)

请参见demo
结果:

> userid | somevalue | dateupdated        
> -----: | :-------- | :----------
>      1 | 573       | 2019-09-20 
>      2 | 234       | 2019-09-11 

答案 1 :(得分:0)

相关子查询通常可以很好地解决此问题:

SELECT B.*
FROM thetable B
WHERE B.DateUpdated = (SELECT MAX(B2.DateUpdated)
                       FROM thetable B2
                       WHERE B2.UserID = B.UserID 
                      );

为了提高性能,您希望在thetable(UserId, DateUpdated)上建立索引。