在日常开发中,经常会遇到这样的需求,查询某张表,要求去重返回最新的一条数据,我们的表是这样的:
| id | name | score | create_time |
| 1 | 姬岚洋 | 90 | 2023-10-17 17:20:44 |
| 2 | 鸡狗 | 89 | 2024-10-17 17:21:44 |
| 3 | 姬岚洋 | 85 | 2024-10-17 17:21:45 |
| 4 | 姬岚洋 | 90 | 2024-10-17 17:22:46 |
传统的写法是这样的:
select * from t_demo where create_time in
(
select max(create_time) from t_demo group by name
)
或者是这样的:
select
t1.*
from t_demo t1
left join t_demo t2 on t1.name = t2.name and t1.create_time < t2.create_time
where t2.id is null
省流直接看这里
但是在MySQL8中引入窗口函数,其中row_number()函数可以完美使用在这个地方,话不多说直接上SQL:
select
id,name,score,create_time
from
(
select id,name,score,create_time,row_number() over (partition by name order by create_time desc) as row_num
from t_demo
) as subquery where row_num = 1
看着好像并没有传统的方式简单,但是这个扩展性非常强,比如你需要多加个聚合字段或者是排序字段,直接在对应的partition by后面和order by后面加就行了,非常好用。
扩展
比如我想取分数最高且时间最新的一条数据,直接order by加上score:
select
id,name,score,create_time
from
(
select id,name,score,create_time,row_number() over (partition by name order by score desc,create_time desc) as row_num
from t_demo
) as subquery where row_num = 1;
结果如下~

3471






