我在这里真的很棘手的SQL语句。尝试构建此查询大约一小时。 也许你可以帮助我。
我们有一个包含3列的表格: gamename |用户| TIMES_PLAYED
查询应该选择前三名游戏(取决于总时间数量)和前三名在此游戏中玩过多次的用户=> 9行。
The result is like:
CounterStrike | Smith
CounterStrike | Jonny
Counterstrike | Hans
WoW | George
WoW | Bob
Wow | Frank
Need For Speed| James
Need For Speed| Marion
Need For Speed| Scarlet
非常好,如果你可以帮助我=) 谢谢!
答案 0 :(得分:13)
<强>更新强>
正如@Steve Kass
指出的那样,我没有注意到你只想要前三场比赛。
以下是更新版本:
在SQL Server
,Oracle
和PostgreSQL 8.4
:
SELECT gamename, user
FROM (
SELECT r.gamename, user,
ROW_NUMBER() OVER (PARTITION BY game ORDER BY times_played DESC) rn,
FROM (
SELECT gamename, ROW_NUMBER() OVER (ORDER BY SUM(times_played) DESC) AS game_rn
FROM results
GROUP BY
gamename
) g
JOIN results r
ON r.gamename = g.gamename
WHERE game_rn <= 3
) q
WHERE rn <= 3
ORDER BY
gamename, times_played DESC
在MySQL
:
SELECT ro.gamename, ro.user
FROM (
SELECT gamename, SUM(times_played) AS rank
FROM results
ORDER BY
rank DESC
LIMIT 3
) rd
JOIN results ro
ON ro.gamename >= rd.gamename
AND ro.gamename <= rd.gamename
AND
(ro.times_played, ro.id) <=
(
SELECT ri.times_played, ri.id
FROM results ri
WHERE ri.gamename = rd.gamename
ORDER BY
ri.times_played DESC, ri.id DESC
LIMIT 2, 1
)
ORDER BY
gamename, times_played DESC
假设此查询被称为PRIMARY KEY
,您将需要id
才能使用此查询。
我的博客中的这篇文章对此进行了更详细的解释:
在PostgreSQL 8.3
及以下:
SELECT gamename, ((ri)[s]).user
FROM (
SELECT gamename, ri, generate_series(1, 3) AS s
FROM (
SELECT ro.gamename,
ARRAY
(
SELECT ri
FROM results ri
WHERE ri.gamename = ro.gamename
ORDER BY
times_played DESC
LIMIT 3
) AS ri
FROM (
SELECT gamename, SUM(times_played) AS rank
FROM results
ORDER BY
rank DESC
LIMIT 3
) rd
) q
) q2
ORDER BY
gamename, s
答案 1 :(得分:1)
我不认为Quassnoi注意到你只要求前三名游戏的最高用户(基于总时间显示)。这是一个查询(未在真实数据上测试,因为没有给出CREATE TABLE和INSERT语句)。我还包括Quassnoi没有的关系,只是为了向你展示这个选项。
with GamesPlays(gamename,totalPlays) as (
select
gamename, sum(times_played)
from results
group by gamename
), GamesRanked(gamename,gameRank) as (
select
gamename,
rank() over (
order by totalPlays desc
)
from GamesPlays
), ResultsRanked(gamename,user,userRank) as (
select
gamename,
user,
rank() over (
partition by user
order by times_played desc
)
from results;
)
select
G.gamename, R.user
from ResultsRanked as R
join GamesRanked as G
on G.gamename = R.gamename
where gameRank <= 3
and userRank <= 3
order by
gameRank,userRank;
答案 2 :(得分:0)
DROP TABLE #game_stats
CREATE TABLE #game_stats (gamename VARCHAR(50),users VARCHAR(50),times_played INT);
INSERT INTO #game_stats VALUES ('Counter Strike','Kamesh',2);
INSERT INTO #game_stats VALUES ('Counter Strike','Hely',4);
INSERT INTO #game_stats VALUES ('Counter Strike','Maitri',1);
INSERT INTO #game_stats VALUES ('Counter Strike','Laxmi',5);
INSERT INTO #game_stats VALUES ('WOW','Kamesh',21);
INSERT INTO #game_stats VALUES ('WOW','laxmi',60);
INSERT INTO #game_stats VALUES ('WOW','Hely',7);
INSERT INTO #game_stats VALUES ('NFS','Hely',5);
INSERT INTO #game_stats VALUES ('NFS','Kamesh',1);
INSERT INTO #game_stats VALUES ('NFS','Maitri',12);
INSERT INTO #game_stats VALUES ('NFS','Laxmi',21);
INSERT INTO #game_stats VALUES ('CODE ZERO','Kamesh',45);
INSERT INTO #game_stats VALUES ('CODE ZERO','Maitri',52);
INSERT INTO #game_stats VALUES ('CODE ZERO','Laxmi',21);
INSERT INTO #game_stats VALUES ('CODE ZERO','Kamesh',41);
INSERT INTO #game_stats VALUES ('HITMAN','Maitri',142);
INSERT INTO #game_stats VALUES ('HITMAN','Laxmi',210);
INSERT INTO #game_stats VALUES ('HITMAN','Kamesh',41);
INSERT INTO #game_stats VALUES ('HITMAN','Maitri',102);
INSERT INTO #game_stats VALUES ('HITMAN','Mani',142);
INSERT INTO #game_stats VALUES ('NFS','Mani',210);
INSERT INTO #game_stats VALUES ('CODE ZERO','Mani',41);
INSERT INTO #game_stats VALUES ('WOW','Mani',102);
select * from #game_stats;
SELECT RN,
Gamename,
Users,
Times_played
FROM
(
SELECT ROW_NUMBER() OVER (PARTITION BY GS.gamename ORDER BY SUM(GS.times_played) DESC) AS RN,
GS.gamename,
GS.users,
SUM(gs.times_played) as times_played
FROM #game_stats GS
WHERE GS.gamename IN (
SELECT TOP 3 gamename
FROM #game_stats
GROUP BY gamename
ORDER BY sum(times_played) DESC
)
GROUP BY GS.gamename,GS.users
) a
WHERE RN<=3
ORDER BY gamename,times_played DESC
答案 3 :(得分:0)
SELECT DISTINCT GN,US,GT,UT
FROM
(SELECT GN,US,GT,UT,
Dense_rank() over(ORDER BY GT DESC) RGT,
Dense_rank() over(partition BY GN ORDER BY UT DESC) RUT
FROM
(SELECT gamename GN,
users US,
times_played TP,
sum(times_played) over (partition BY gamename) GT ,
sum(times_played) over (partition BY gamename,users) UT
FROM game_stats))
WHERE RGT <4
AND RUT < 4
ORDER BY GT DESC,
UT DESC