Nemám žádné PostgreSQL pozadí, ale uvidíme, jestli to funguje:
Začal bych tím, že to zjednoduším, napsáním dotazu, který nejprve vrátí celkové skóre hráče:
SELECT player_id, SUM(score) score
FROM (
SELECT first_player as player_id, first_score as score
FROM matches
UNION ALL
SELECT second_player, second_score
FROM matches
)
GROUP BY player_id
Nyní připojte tuto datovou sadu k hráčům a najděte skupiny:
SELECT w.player_id, p.group_id, w.score
FROM
(
SELECT player_id, SUM(score) score
FROM (
SELECT first_player as player_id, first_score as score
FROM matches
UNION ALL
SELECT second_player, second_score
FROM matches
)
GROUP BY player_id
) as w
inner join players p
on p.player_id = w.player_id
Nyní máme všechny hráče, jejich celkové skóre a jejich skupinu. Chceme určit vítěze podle skupiny? Můžeme použít hodnocení funkce k tomu:
SELECT
w.player_id,
p.group_id,
w.score,
RANK() OVER (PARTITION BY p.group_id ORDER BY score DESC) as group_placement
FROM
(
SELECT player_id, SUM(score) score
FROM (
SELECT first_player as player_id, first_score as score
FROM matches
UNION ALL
SELECT second_player, second_score
FROM matches
)
GROUP BY player_id
) as w
inner join players p
on p.player_id = w.player_id
Nyní pouze vybereme ty nejlepší v každé skupině (hodnocení =1) pomocí WHERE
SELECT
player_id,
group_id
FROM
(
SELECT
w.player_id,
p.group_id,
w.score,
RANK() OVER (PARTITION BY p.group_id ORDER BY score DESC) as group_placement
FROM
(
SELECT player_id, SUM(score) score
FROM (
SELECT first_player as player_id, first_score as score
FROM matches
UNION ALL
SELECT second_player, second_score
FROM matches
)
GROUP BY player_id
) as w
inner join players p
on p.player_id = w.player_id
) as gp
WHERE group_placement = 1
Vypadá to složitě? ano, ale můžete vidět, že konečný výsledek je poskytován kousek po kousku. Každý krok je „podtabulkou“ a můžete spustit a sledovat data v každém bodě.