1

我真的很难创建一个选择语句,它将为每个用户返回最快时间的记录。如果秒数相同,则应选择最低的“点击次数”。

如果我的表中有以下记录

user    seconds     clicks
1       10.23       10
1       10.12       12
1       10.12       14
2       12.11       16
3       12.34       18
3       12.00       16

我需要每个用户最少的时间和点击次数,所以我需要一个查询来返回

user    seconds    clicks
1       10.12       12
2       12.11       16
3       12.00       16

我试过的查询是

select user, min(seconds), min(clicks) from mytable group by user

但它选择秒 10.12 并为用户 1 单击 10,这是不正确的。我可以在 1 个查询中执行此操作吗?

4

3 回答 3

0

尝试与 self 进行内部连接,如下所示:

 select a.user, a.seconds, a.clicks 
 from mytable a JOIN
      (SELECT user, min(seconds) as MIN_SECONDS
       FROM mytable 
       GROUP BY USER) AS b
 ON a.user = b.user AND a.seconds = b.MIN_SECONDS;
于 2012-12-09T21:02:14.083 回答
0

这是greatest-n-per-group经常出现的问题的变体。

SELECT m.*
FROM mytable AS m
LEFT OUTER JOIN mytable AS m2 ON m.user = m2.user
  AND (m.seconds > m2.seconds OR m.seconds = m2.seconds AND m.clicks > m2.clicks)
WHERE m2.user IS NULL;

解释:

我们希望m成为每个用户拥有最低秒数的行,或者如果最低秒数相同,则点击次数最低。换句话说,该用户不应该有其他具有较低秒数或较低点击次数的行。

使用排除联接尝试查找具有较低秒数或较低点击次数的任何行。如果没有找到这样的行,m则为具有最低值的行。


如果有多行的秒数点击次数最少,则仍然可能导致平局并为用户返回多行。在这种情况下,您需要解决与其他列的关系,希望是唯一的列。

例子:

SELECT m.*
FROM mytable AS m
LEFT OUTER JOIN mytable AS m2 ON m.user = m2.user
  AND (m.seconds > m2.seconds OR m.seconds = m2.seconds AND (m.clicks > m2.clicks
  OR m.clicks = m2.clicks AND m.id > m2.id))
WHERE m2.user IS NULL;
于 2012-12-09T21:04:28.417 回答
0

这应该工作

SELECT c.userid, c.seconds, min(c.clicks) FROM clicks as c
INNER JOIN (select userid, min(seconds) as s from clicks group by userid) AS sq 
ON (c.userid=sq.userid AND c.seconds=sq.s) group by c.userid;

但没有任何加入就无法完成。

您可能必须更改列和表的名称。

于 2012-12-09T21:47:09.437 回答