Skip to content
튜닝 연습서브쿼리와 쿼리 변환
SUBQ-032

리뷰 요청 대상 「지난주 평가 없는 상품」이 4주째 0개이고, 실행은 0.01초도 안 걸린다

기초SELECT한빛유통267 / 700

상황 ​

상품팀은 매주 월요일 09시에 「리뷰 요청 대상」을 뽑는다. 지난주(월요일 0시부터 이번 주 월요일 0시 전까지) 평가가 한 건도 들어오지 않은 상품을 고르고, 그 상품을 산 고객에게 리뷰를 부탁하는 알림을 보낸다. 지난달 조민우가 이 SQL을 ANSI 외부 조인으로 다시 쓴 뒤로 4주 내리 대상이 0개다. 조민우는 "평가가 고르게 들어와서 그런 것 같다. 실행도 0.01초가 안 걸린다"라고 하지만, 상품팀이 화면에서 세어 보면 평가가 없는 상품이 매주 20개 넘게 있다.

테이블과 인덱스 ​

  • M_ITM 상품: 100행 · 5블록 · PK_M_ITM (ITM_ID)
  • T_ITM_EVL 상품평가: 5,000행 · 48블록 · PK_T_ITM_EVL (ITM_ID, EVL_LST_NO) · ITM_ID는 NOT NULL · EVL_DT DATE(2024년, 하루 13 ~ 14건)
  • 2024-06-10 ~ 06-16 한 주의 평가는 98건이고, 평가를 받은 상품은 76개다
  • 통계 최신 · 바인드는 DATE(:v_from = DATE '2024-06-10', :v_to = DATE '2024-06-17')

원본 SQL ​

sql
SELECT i.ITM_ID, i.ITM_NM
  FROM M_ITM i
  LEFT OUTER JOIN T_ITM_EVL e
    ON e.ITM_ID = i.ITM_ID
 WHERE e.EVL_DT >= :v_from
   AND e.EVL_DT <  :v_to
   AND e.ITM_ID IS NULL
 ORDER BY i.ITM_ID

실행계획 학습용 예시 · 행 수는 적재 데이터 그대로 ​

xplan
----------------------------------------------------------------------------------------------
| Id  | Operation            | Name      | Starts | E-Rows | A-Rows |   A-Time   | Buffers |
----------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT     |           |      1 |        |      0 |00:00:00.01 |       0 |
|   1 |  SORT ORDER BY       |           |      1 |      1 |      0 |00:00:00.01 |       0 |
|*  2 |   FILTER             |           |      1 |        |      0 |00:00:00.01 |       0 |
|*  3 |    HASH JOIN         |           |      0 |      1 |      0 |00:00:00.01 |       0 |
|*  4 |     TABLE ACCESS FULL| T_ITM_EVL |      0 |     96 |      0 |00:00:00.01 |       0 |
|   5 |     TABLE ACCESS FULL| M_ITM     |      0 |    100 |      0 |00:00:00.01 |       0 |
----------------------------------------------------------------------------------------------

Predicate Information (identified by operation id):
---------------------------------------------------
   2 - filter(NULL IS NOT NULL)
   3 - access("E"."ITM_ID"="I"."ITM_ID")
   4 - filter(("E"."EVL_DT">=:V_FROM AND "E"."EVL_DT"<:V_TO))

문제 ​

  1. 결과가 0개인 까닭을 외부 조인과 WHERE 절의 관계로 설명하시오. 실행계획 2번 줄의 조건과 3 ~ 5번 줄의 Starts가 무엇을 뜻하는지도 설명하시오.
  2. 지난주 평가가 없는 상품이 나오도록 SQL을 고치시오.
원본 SQL을 고쳐 쓰세요. 인덱스 DDL과 힌트도 쓸 수 있습니다.
무엇이 문제였고 왜 이렇게 고쳤는지 쓰세요.0자