我有下表:
id time text otheridentifier
-------------------------------------------
1 6 apple 4
2 7 orange 4
3 8 banana 3
4 9 pear 3
5 10 grape 2
我想要做的是选择3个最近的记录(按时间desc),其otheridentifier
是不同的。所以在这种情况下,结果将是id
:5,4和2。
id
= 3将被跳过,因为最近的记录具有相同的otheridentifier
字段。
这是我试图做的事情:
SELECT * FROM `table` GROUP BY (`otheridentifier`) ORDER BY `time` DESC LIMIT 3
但是,我最终得到id
= 5, 3 和 1 的行,而不是预期的5,4,2行。
有人可以告诉我为什么这个查询不会返回我的预期吗?我尝试将ORDER BY更改为ASC,但这只是将返回的行重新排列为1,3,5。
答案 0 :(得分:34)
它没有返回您的期望,因为在排序之前发生了分组,这反映在SQL语句中子句的位置。不幸的是,你必须得到更好的方法来获得你想要的行。试试这个:
SELECT *
FROM `table`
WHERE `id` = (
SELECT `id`
FROM `table` as `alt`
WHERE `alt`.`otheridentifier` = `table`.`otheridentifier`
ORDER BY `time` DESC
LIMIT 1
)
ORDER BY `time` DESC
LIMIT 3
答案 1 :(得分:18)
您可以自己加入表格来过滤每个otheridentifier
的最后一个条目,然后取出前3行:
SELECT last.*
FROM `table` last
LEFT JOIN `table` prev
ON prev.`otheridentifier` = last.`otheridentifier`
AND prev.`time` < last.`time`
WHERE prev.`id` is null
ORDER BY last.`time` DESC
LIMIT 3
答案 2 :(得分:4)
我有类似的要求,但我有更高级的选择标准。使用其他一些答案我无法得到我需要的东西,但我发现你仍然可以在这之后进行GROUP BY和ORDER BY:
SELECT t.* FROM (SELECT * FROM table ORDER BY time DESC) t
GROUP BY t.otheridentifier
答案 3 :(得分:2)
SELECT * FROM table t1
WHERE t1.time =
(SELECT MAX(time) FROM table t2
WHERE t2.otheridentifier = t1.otheridentifier)
答案 4 :(得分:2)
Andomar's answer可能是最好的,因为它不使用子查询。
另一种方法:
select *
from `table` t1
where t1.`time` in (
select max(s2.`time`)
from `table` t2
group by t2.otheridentifier
)
答案 5 :(得分:2)
您可以使用此查询获得正确答案:
SELECT * FROM
(SELECT * FROM `table` order by time DESC)
t group by otheridentifier
答案 6 :(得分:1)
怎么样
SELECT *, max(time) FROM `table` group by otheridentifier
答案 7 :(得分:0)
这也是:
SELECT * FROM
OrigTable T INNER JOIN
(
SELECT otheridentifier,max(time) AS duration
FROM T
GROUP BY otheridentifier) S
ON S.duration = T.time AND S.otheridentifier = T.otheridentifier.