我有一个像这样的 MYSQL 表:
id | userid | score | datestamp |
-----------------------------------------------------
1 | 1 | 5 | 2012-12-06 03:55:16
2 | 2 | 0,5 | 2012-12-06 04:25:21
3 | 1 | 7 | 2012-12-06 04:35:33
4 | 3 | 12 | 2012-12-06 04:55:45
5 | 2 | 22 | 2012-12-06 05:25:11
6 | 1 | 16,5 | 2012-12-06 05:55:21
7 | 1 | 19 | 2012-12-06 13:55:16
8 | 2 | 8,5 | 2012-12-07 06:27:16
9 | 2 | 7,5 | 2012-12-07 08:33:16
10 | 1 | 10 | 2012-12-07 09:25:19
11 | 1 | 6,5 | 2012-12-07 13:33:16
12 | 3 | 6 | 2012-12-07 15:45:44
13 | 2 | 4 | 2012-12-07 16:05:16
14 | 2 | 34 | 2012-12-07 18:33:55
15 | 2 | 22 | 2012-12-07 18:42:11
我想像这样显示用户分数: 如果某个用户在某一天的得分超过 3 个,它只会获得最高的 3 个,每天为该用户重复该操作,然后将所有天数加在一起。我想为每个用户显示这个总和。
编辑: 因此,在上面的示例中,用户 1 在 06.12 上。我会将前 3 名得分加在一起并忽略第 4 名得分,然后从第二天开始将前 3 名加到该数字上,依此类推。我需要每个用户的那个号码。
编辑 2: 预期输出是:
userid | score
--------------------
1 | 59 //19 + 16.5 + 7 (06.12.) + 10 + 6.5 (07.12.)
2 | 87 //22 + 0.5 (06.12.) + 34 + 22 + 8.5 (07.12.)
3 | 18 //12 (06.12.) + 6 (07.12.)
我希望这更清楚:)
我真的很感激你的帮助,因为我被困住了。
最佳答案
请看下面的代码,如果你对我的评论的回答是yes
:) 因为你的数据都是 2012 年的,而且是 11 月份,我花了一天。
查询:
select y.id, y.userid, y.score, y.datestamp
from (select id, userid, score, datestamp
from scores
group by day(datestamp)) as y
where (select count(*)
from (select id, userid, score, datestamp
from scores group by day(datestamp)) as x
where y.score >= x.score
and y.userid = x.userid
) =1 -- Top 3rd, 2nd, 1st
order by y.score desc
;
结果:
ID USERID SCORE DATESTAMP
8 2 8.5 December, 07 2012 00:00:00+0000
20 3 6 December, 08 2012 00:00:00+0000
1 1 5 December, 06 2012 00:00:00+0000
基于您对问题的最新更新。
如果您需要按年/月/日对每个用户进行一些查询,然后找到最高的,您可以简单地在上面的查询中添加像 sum
这样的聚合函数。我正在重复自己,因为你的样本数据只有一年,所以没有按年或按月的点组。这就是我休息一天的原因。
select y.id, y.userid, y.score, y.datestamp
from (select id, userid, sum(score) as score,
datestamp
from scores
group by userid, day(datestamp)) as y
where (select count(*)
from (select id, userid, sum(score) as score
, datestamp
from scores
group by userid, day(datestamp)) as x
where y.score >= x.score
and y.userid = x.userid
) =1 -- Top 3rd, 2nd, 1st
order by y.score desc
;
基于总和的结果:
ID USERID SCORE DATESTAMP
1 1 47.5 December, 06 2012 00:00:00+0000
8 2 16 December, 07 2012 00:00:00+0000
20 3 6 December, 08 2012 00:00:00+0000
更新了新的源数据样本
Simon,请看一下我自己的样本。随着您的数据不断变化,我使用了我的。
这是引用。我使用了纯 ansi
风格,没有任何 over partition
或 dense_rank
。
另请注意,我使用的数据是前 2 名而不是前 3 名。您可以相应地进行更改。
猜猜看,答案比你的第一个数据给人的第一印象简单 10 倍......
SQLFIDDLE
查询到 1: -- 用户每天前 2 的总和
SELECT userid, sum(Score), datestamp
FROM scores t1
where 2 >=
(SELECT count(*)
from scores t2
where t1.score <= t2.score
and t1.userid = t2.userid
and day(t1.datestamp) = day(t2.datestamp)
order by t2.score desc)
group by userid, datestamp
;
查询 1 的结果:
USERID SUM(SCORE) DATESTAMP
1 70 December, 06 2012 00:00:00+0000
1 30 December, 07 2012 00:00:00+0000
2 22 December, 06 2012 00:00:00+0000
2 25 December, 07 2012 00:00:00+0000
3 30 December, 06 2012 00:00:00+0000
3 30 December, 07 2012 00:00:00+0000
最终查询: -- 用户所有两天前 2 总和
SELECT userid, sum(Score)
FROM scores t1
where 2 >=
(SELECT count(*)
from scores t2
where t1.score <= t2.score
and t1.userid = t2.userid
and day(t1.datestamp) = day(t2.datestamp)
order by t2.score desc)
group by userid
;
最终结果:
USERID SUM(SCORE)
1 100
2 47
3 60
这是我使用的数据直接计算的快照。
关于mysql - 为每个用户选择每天最高的 3 个分数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13763855/