HackerRank Contest Leaderboard
해커의 총 점수가 모든 챌린지에서 최고 점수의 합계로 계산될 때, hacker_id, name, 총 점수를 출력하는 문제이다.
결과는 총 점수 내림차순으로 정렬하고, 만약 여러 해커가 같은 총 점수를 가졌다면 hacker_id 오름차순으로 정렬해야 한다.
또한, 총 점수가 0인 해커는 결과에서 제외해야 한다.
서브 쿼리로 각 해커의 챌린지별 최고 점수를 뽑고, 이걸 HACKER 테이블과 조인하여 풀었다.
-- 정답
SELECT
H.HACKER_ID,
H.NAME,
SUM(M.SCORE) AS TOTAL_SCORE
FROM
HACKERS AS H
LEFT JOIN (
SELECT HACKER_ID, MAX(SCORE) AS SCORE
FROM SUBMISSIONS
GROUP BY HACKER_ID, CHALLENGE_ID
) AS M
ON
H.HACKER_ID = M.HACKER_ID
GROUP BY
H.HACKER_ID,
H.NAME
HAVING
SUM(M.SCORE) != 0
ORDER BY
SUM(M.SCORE) DESC,
HACKER_ID ASC;
위 쿼리의 SUM(M.SCORE) != 0을 HAVING 절이 아닌 WHERE 절에 써도 될까? 불가능하다!
WHERE 절은 각 행별로 조건을 판단하는데, 반면 집계 함수는 그룹화 후 데이터를 처리하기 때문이다.
따라서 집계 후 조건은 HAVING 절에서 처리해야 한다.
-- 오답
SELECT
H.HACKER_ID,
H.NAME,
SUM(M.SCORE) AS TOTAL_SCORE
FROM
HACKERS AS H
LEFT JOIN (
SELECT HACKER_ID, MAX(SCORE) AS SCORE
FROM SUBMISSIONS
GROUP BY HACKER_ID, CHALLENGE_ID
) AS M
ON
H.HACKER_ID = M.HACKER_ID
WHERE
SUM(M.SCORE) != 0
GROUP BY
H.HACKER_ID,
H.NAME
ORDER BY
SUM(M.SCORE) DESC,
HACKER_ID ASC;