Mysql按聚合排序和限制分组[重复]
Posted
技术标签:
【中文标题】Mysql按聚合排序和限制分组[重复]【英文标题】:Mysql group by aggregation sort and limit [duplicate] 【发布时间】:2021-01-06 04:08:09 【问题描述】:我试图找出一个看似微不足道的 SQL 查询。 对于表中的所有用户,我想查找时间最长的行(最新事件)的时间和数据。
下面的差不多就解决了
SELECT user, MAX(time) as time FROM tasks GROUP BY user;
问题当然是不能减少data
列。我认为因此我应该使用 WHERE 或 ORDER BY + LIMIT 结构。但是我离我的领域太远了,不知道应该如何正确完成。有什么提示吗?
注意。在这种情况下无法使用 GROUP BY,因为我想在表行 ID 上进行选择,显然无法聚合。
-- mysql
DROP DATABASE IF EXISTS test;
CREATE DATABASE test;
USE test;
CREATE TABLE tasks (
id int AUTO_INCREMENT,
user varchar(100) NOT NULL,
time date NOT NULL,
data varchar(100) NOT NULL,
PRIMARY KEY (id)
);
INSERT INTO tasks (user, time, data) VALUES
("Kalle", "1970-01-01", "old news"),
("Kalle", "2020-01-01", "latest shit"),
("Pelle", "1970-01-01", "regular data");
-- Expected output
-- +----+-------+------------+--------------+
-- | id | user | time | data |
-- +----+-------+------------+--------------+
-- | 2 | Kalle | 2020-01-01 | latest shit |
-- | 3 | Pelle | 1970-01-01 | regular data |
-- +----+-------+------------+--------------+
-- 2 rows in set (0.00 sec)
【问题讨论】:
Please don't post screenshots of text。它们无法被搜索或复制,并且可用性差。相反,将代码作为文本直接粘贴到您的问题中。如果选择它并单击
按钮或Ctrl+K,则代码块将缩进四个空格,这将导致其呈现为代码。
我不会在封闭的地方工作。如果其他人可以从中学习,我很乐意修改 Q 的形式。
此问题已关闭,但未已删除。作为重复关闭的问题(例如这个)通常对未来的用户有用,因为它们提供了额外的搜索目标。如果您在文件中有上述内容,您唯一需要做的“工作”就是复制该文本,edit 这个问题,将文本粘贴到图像上,再次选择代码,然后按 Ctrl+K 或单击
按钮将其格式化为代码。
我按照建议更新了 Q。
【参考方案1】:
您可以使用子查询进行过滤:
select t.*
from tasks t
where time = (select max(t1.time) from tasks t1 where t1.user = t.user)
此查询将利用(user, time)
上的多列索引。
在 MySQL 8.0 中,您还可以使用窗口函数解决此 top-1-per-group:
select *
from (select t.*, row_number() over(partition by user order by time desc) rn from tasks t) t
where rn = 1
【讨论】:
多列索引是否比使用 Id 列更可取?而不是使用where time = ...
使用where id = ...
并为用户选择最新任务的ID?
@user3504575:这两个选项都可以,这取决于您如何定义 latest 任务。以上是关于Mysql按聚合排序和限制分组[重复]的主要内容,如果未能解决你的问题,请参考以下文章