포스트

조건에 맞는 사용자와 총 거래금액 조회하기

https://school.programmers.co.kr/learn/courses/30/lessons/164668

문제 문제

  • 문제 풀이

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    
      SELECT
          B.WRITER_ID,
          U.NICKNAME,
          SUM(B.PRICE) AS "TOTAL_SALES"
      FROM
          USED_GOODS_BOARD B
      JOIN
          USED_GOODS_USER U
      ON
          B.WRITER_ID = U.USER_ID AND B.STATUS = 'DONE'
      GROUP BY
          B.WRITER_ID, U.NICKNAME
      HAVING
          SUM(B.PRICE) >= 700000
      ORDER BY
          TOTAL_SALES;
    
    • “USED_GOODS_BOARD” 테이블과 “USED_GOODS_USER” 테이블을 조인하고, “STATUS”가 ‘DONE’인 행만 선택한 후, 판매자별로 총 판매액을 계산한다. 그런 다음, 총 판매액이 700,000 이상인 판매자를 선택하고, 그 결과를 “TOTAL_SALES” 열을 기준으로 오름차순으로 정렬한다. 이 쿼리는 조건에 따라 필터링하고, 집계 함수인 SUM을 사용하여 총 판매액을 계산한다.


  • HAVING 절은 주로 그룹화된 결과에 대한 조건을 지정하는 데 사용되며, 필터링 조건은 WHERE 절에 위치하는 것이 일반적이다.

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    
      SELECT 
          B.WRITER_ID, 
          U.NICKNAME, 
          SUM(B.PRICE) AS "TOTAL_SALES"
      FROM 
          USED_GOODS_BOARD B
      JOIN 
          USED_GOODS_USER U
      ON 
          B.WRITER_ID = U.USER_ID
      WHERE 
          B.STATUS = 'DONE'
      GROUP BY 
          B.WRITER_ID, U.NICKNAME
      HAVING 
          SUM(B.PRICE) >= 700000
      ORDER BY 
          TOTAL_SALES;
    
    • HAVING 절은 GROUP BY 절 다음에 오며, 그룹화된 결과에 대한 조건을 처리한다. 이 절은 주로 집계 함수 (예: SUM, COUNT, AVG 등)를 사용한 그룹화된 데이터에 대한 조건을 지정할 때 사용된다.
    • WHERE 절은 데이터를 추출하기 전에 필터링을 수행하는 역할을 한다. 그래서 B.STATUS = 'DONE'과 같은 필터링 조건은 WHERE 절에 두어야 한다. 이렇게 하면 INNER JOIN이나 다른 조인 종류를 사용한 후에도 해당 조건에 따라 필요한 데이터만 추출된다.


  • 레코드를 필터링하는 조건은 특히 집계되지 않은 열에 대한 경우 GROUP BY 절 이전에 오는 것이 올바르다.

    실행 결과

    • 쿼리에 문제가 있는 이유는 HAVING 절이 GROUP BY 연산 이후에 적용되기 때문이다. 여러 개의 행을 하나로 그룹화한 후에 그룹화된 결과에 대한 조건을 적용하기 때문에 B.STATUS = 'DONE'과 같은 비집계 컬럼은 GROUP BY 절에 포함되지 않았기 때문에 오류가 발생한다.
    • 이 문제를 해결하기 위해 WHERE 절에 조건을 이동시키고, 그룹화된 결과에 대한 조건은 HAVING 절에서 적용하면 된다. 수정하면 B.STATUS = 'DONE' 조건이 그룹화 이전에 적용되고, 그룹화된 결과에 대한 조건은 HAVING 절에서 적용되어 올바르게 동작할 것이다.


  • 실행 결과

실행 결과

이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.