Get maximum from aggregated values in a query I have a table details it has a column kills and a column player_slot and a column match_id. I want to find the maximum difference between the SUM of kills for player_slot 0-4 and 128-132. Can someone give me a hint?

Thats my table details:

id,
kills,
match_id,
player_id,
player_slot


Thats what I got so far, it's not much:

SELECT SUM(m."kills") AS max_kills
FROM details m
INNER JOIN matches ON matches.id = m.match_id
WHERE m.player_slot IN (0,1,2,3,4)
GROUP BY m."match_id"

SELECT SUM(m."kills") AS max_kills
FROM details m
INNER JOIN matches ON matches.id = m.match_id
WHERE m.player_slot IN (128,129,130,131,132)
GROUP BY m."match_id"
SELECT *
FROM  (
   SELECT match_id
         ,SUM(CASE WHEN d.player_slot BETWEEN   0 AND   4
                   THEN d.kills ELSE 0 END) AS team1_kills
         ,SUM(CASE WHEN d.player_slot BETWEEN 128 AND 132
                   THEN d.kills ELSE 0 END) AS team2_kills
   FROM   details d
   WHERE (d.player_slot BETWEEN   0 AND   4
      OR  d.player_slot BETWEEN 128 AND 132) -- parens optional
   GROUP  BY d.match_id
   ) sub
ORDER  BY @(team1_kills - team2_kills) DESC
LIMIT  1;


The subquery is only for convenience.

The WHERE can might improve performance if a matching index is available. Redundant otherwise.

The CASE statements sum only kills from qualified players.

The @- operator produces the absolute value of the score difference. This is used to sort by (descending), then we only need to pick the first.

Don't use m as table alias for details, when a second table called matches is involved. That's confusing. Using d instead.

More generally, why do you join to matches at all? It is not used in the query. Are there details without associated match to exclude? (Then it would make sense.)


Based on comments
The query could probably be simpler / faster this way:
SELECT *
FROM  (
   SELECT match_id
         ,SUM(CASE WHEN p.team_id = ? THEN d.kills ELSE 0 END) AS team1_kills -- team1
         ,SUM(CASE WHEN p.team_id = ? THEN d.kills ELSE 0 END) AS team2_kills -- team2
   FROM   details d
   JOIN   players p ON p.id = d.player_slot  -- guessing from comment
   WHERE  p.team_id  IN (?, ?)               -- teams to compare go here.
   GROUP  BY d.match_id
   ) sub
ORDER  BY @(team1_kills - team2_kills) DESC
LIMIT  1;