테마
「당일 상품별 판매 현황」은 5분마다 오늘 주문을 상품별로 묶어 요약 테이블에 다시 적재한다(하루 288번). 예전에는 상품 100개를 하나씩 돌며 집계했는데, 지난달 조민우가 INSERT ... SELECT 한 문장으로 바꿨다.
조민우는 "상품별 집계라서 상품부터 읽도록 힌트를 달았다"라고 한다. 적재 한 번은 1초 남짓이지만, 하루 288번 돌면서 서버의 논리 읽기 상위에 올라 있다. 아래는 2024-06-14 한 번의 실행계획이다.
T_ORD: 100,000행 · 896블록 · PK_T_ORD (ORD_SEQ) · IX_T_ORD_DT (ORD_DT) · 하루 137건이고, 하루치 주문은 테이블 전체에 흩어져 있다T_ORD_DET: 200,000행 · 896블록 · PK_T_ORD_DET (ORD_SEQ, ORD_DET_NO) · IX_T_ORD_DET_ITM (ITM_ID) (상품 화면용) · 상품마다 2,000줄 · 2024-06-14 주문상세는 274줄 (상품 30종)M_ITM: 100행 · 5블록 · PK_M_ITM (ITM_ID)T_ITM_DAY_SLS (BAS_DT, ITM_ID, ORD_CNT, ORD_QTY, ORD_AMT): 적재 전에 그날 행을 지운다 · 인덱스 없음 · 통계 최신INSERT INTO T_ITM_DAY_SLS (BAS_DT, ITM_ID, ORD_CNT, ORD_QTY, ORD_AMT)
SELECT /*+ LEADING(m d o) USE_NL(d o) */
:v_dt, m.ITM_ID, COUNT(DISTINCT o.ORD_SEQ), SUM(d.ORD_QTY), SUM(d.ORD_QTY * d.UNT_PRC)
FROM M_ITM m, T_ORD_DET d, T_ORD o
WHERE d.ITM_ID = m.ITM_ID
AND o.ORD_SEQ = d.ORD_SEQ
AND o.ORD_DT >= :v_dt
AND o.ORD_DT < :v_dt + 1
GROUP BY m.ITM_ID
----------------------------------------------------------------------------------------------------------------
| Id | Operation | Name | Starts | E-Rows | A-Rows | A-Time | Buffers |
----------------------------------------------------------------------------------------------------------------
| 0 | INSERT STATEMENT | | 1 | | 0 |00:00:01.21 | 331K |
| 1 | LOAD TABLE CONVENTIONAL | T_ITM_DAY_SLS | 1 | | 0 |00:00:01.21 | 331K |
| 2 | HASH GROUP BY | | 1 | 100 | 30 |00:00:01.21 | 331K |
| 3 | NESTED LOOPS | | 1 | 274 | 274 |00:00:01.20 | 331K |
| 4 | NESTED LOOPS | | 1 | 200K | 200K |00:00:00.52 | 131K |
| 5 | NESTED LOOPS | | 1 | 200K | 200K |00:00:00.31 | 90205 |
| 6 | INDEX FULL SCAN | PK_M_ITM | 1 | 100 | 100 |00:00:00.01 | 1 |
| 7 | TABLE ACCESS BY INDEX ROWID | T_ORD_DET | 100 | 2000 | 200K |00:00:00.28 | 90204 |
|* 8 | INDEX RANGE SCAN | IX_T_ORD_DET_ITM | 100 | 2000 | 200K |00:00:00.04 | 604 |
|* 9 | INDEX UNIQUE SCAN | PK_T_ORD | 200K | 1 | 200K |00:00:00.15 | 40612 |
|* 10 | TABLE ACCESS BY INDEX ROWID | T_ORD | 200K | 1 | 274 |00:00:00.62 | 200K |
----------------------------------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
8 - access("D"."ITM_ID"="M"."ITM_ID")
9 - access("O"."ORD_SEQ"="D"."ORD_SEQ")
10 - filter(("O"."ORD_DT">=:V_DT AND "O"."ORD_DT"<:V_DT+1))
Starts와 A-Rows를 따라가며, 그날 주문상세 274줄을 얻으려고 몇 행을 거쳤는지 설명하시오.