El agregado FILTER
cláusula en Postgres 9.4 o más reciente es más corto y más rápido:
SELECT u.name
, count(*) FILTER (WHERE g.winner_id > 0) AS played
, count(*) FILTER (WHERE g.winner_id = u.id) AS won
, count(*) FILTER (WHERE g.winner_id <> u.id) AS lost
FROM games g
JOIN users u ON u.id IN (g.player_1_id, g.player_2_id)
GROUP BY u.name;
- El manual
- Wiki de PostgreSQL
- Entrada de blog de Depesz
En Postgres 9.3 (o cualquiera versión) esto es aún más corto y rápido que las subselecciones anidadas o CASE
expresiones:
SELECT u.name
, count(g.winner_id > 0 OR NULL) AS played
, count(g.winner_id = u.id OR NULL) AS won
, count(g.winner_id <> u.id OR NULL) AS lost
FROM games g
JOIN users u ON u.id IN (g.player_1_id, g.player_2_id)
GROUP BY u.name;
Detalles:
- Para un rendimiento absoluto, ¿SUM es más rápido o COUNT?