Conditional SQL Count
Answer : Use the aggregate FILTER option in Postgres 9.4 or later: SELECT category , count(*) FILTER (WHERE question1 = 0) AS zero , count(*) FILTER (WHERE question1 = 1) AS one , count(*) FILTER (WHERE question1 = 2) AS two FROM reviews GROUP BY 1; Details for the FILTER clause: Aggregate columns with additional (distinct) filters If you want it short : SELECT category , count(question1 = 0 OR NULL) AS zero , count(question1 = 1 OR NULL) AS one , count(question1 = 2 OR NULL) AS two FROM reviews GROUP BY 1; Overview over possible variants: For absolute performance, is SUM faster or COUNT? Proper crosstab query crosstab() yields the best performance and is shorter for longer lists of options: SELECT * FROM crosstab( 'SELECT category, question1, count(*) AS ct FROM reviews GROUP BY 1, 2 ORDER BY 1, 2' , 'VALUES (0), (1), (2)' ) AS ct (category text, zero int, one int, two int); Detailed explanation...