FULL OUTER JOIN 을 UNION ALL + NOT EXISTS 로 변환
FULL OUTER JOIN 은 OUTER JOIN + UNION ALL + NOT EXISTS 세 조각으로 분해할 수 있습니다. 핵심 정리 FULL OUTER JOIN ≡ (A 기준 OUTER JOIN) UNION (B 기준 OUTER JOIN) — 양쪽의 unmatched row 까지 모두 보존하기 위한 합집합입니다. 두 번째 SEL...
FILTER PUSH DOWN 을 위해 ROWNUM, RANK 제거
인라인 뷰 안의 RANK/ROWNUM 같은 결과집합 의존 함수가 있으면 옵티마이저는 외부 술어를 뷰 안으로 푸시 다운 하지 않습니다. 불필요한 RANK 를 제거하니 EMP_JOB_IX 인덱스 RANGE SCAN 으로 처리되어 풀스캔과 WINDOW SORT 가 사라집니다.
EXISTS 로 JOIN 조건을 대체 (Filter)
결과에 컬럼이 없는 1:1 PK Join 이 단순 필터 용도로 끼어 있다면 — JOIN 을 EXISTS 서브쿼리로 빼고 /*+ NO_UNNEST */ 로 FILTER 처리를 강제해 서브쿼리 캐시 효과로 I/O 를 줄일 수 있습니다. 핵심 정리 FILTER 로 빠지는 서브쿼리는 인풋 키의 distinct 가 적을수록 캐시 적중률이 높아져 I/...
EXISTS 로 DISTINCT 구문을 대체 (Filter, Semi Join)
1:N JOIN 의 N 쪽을 EXISTS 로 빼낸 뒤, NO_UNNEST 로 FILTER, UNNEST + NL_SJ 로 SEMI JOIN 을 각각 강제하는 두 길을 같은 데이터(T_CUST × T_ORDER3) 에서 trace 로 비교합니다.
DISTINCT 를 INDEX UNIQUE SCAN으로 제거
옵티마이저가 결과 row의 유일성을 이미 보장한다고 판단하면 DISTINCT를 위한 HASH/SORT UNIQUE 단계가 자동으로 사라집니다. PK·UNIQUE 인덱스 활용이 곧 옵티마이저에게 '중복 제거 불필요'임을 알려주는 일임을 실행계획으로 보여줍니다.
DISTINCT 를 1대N 관계 에서 N 을 Nested Subquery 로 전환해 제거 (2)
1대N JOIN의 N쪽을 EXISTS 서브쿼리로 빼낸 뒤, UNNEST + NL_SJ 힌트로 NESTED LOOPS SEMI를, NO_UNNEST로 FILTER를 강제하는 옵티마이저 컨트롤.
DISTINCT 를 1대N 관계에서 N 을 Nested Subquery 로 전환해 제거 (1)
1대N JOIN에서 결과 컬럼이 1쪽만 필요한데 N쪽 때문에 DISTINCT가 강제되었다면, N쪽을 EXISTS 서브쿼리로 분리하는 것만으로 row 폭증과 DISTINCT 비용을 동시에 제거할 수 있습니다. 옵티마이저에게 '체크용'임을 알려주는 패턴을 실행계획 비교로 풀어냅니다.
PostgreSQL은 왜 shared_buffers를 25%만 권고하고, Aurora는 왜 75%일까?
PostgreSQL은 25%, Aurora는 75% — 같은 엔진인데 권고치가 정반대인 이유를, OS 페이지 캐시를 2차 캐시로 활용하는 PostgreSQL의 디자인 철학과 OS 캐시를 우회하도록 재설계된 Aurora의 분리 스토리지 구조에서 찾습니다.
COUNT(컬럼) 을 COUNT(*) 로 대체
NOT NULL 제약조건이 선언되어 있으면 옵티마이저가 COUNT(컬럼)을 COUNT(*)로 자동 변환해, 테이블 접근 없이 인덱스만으로 처리할 수 있습니다. 물리 모델 설계 단계에서 NOT NULL 명시가 곧 성능 최적화임을 실행계획으로 검증합니다.
PostgreSQL 커뮤니티 패치 리뷰 — XLOG_SWITCH 반환값 일관성 (#6680)
DBA로서 PostgreSQL 오픈소스 커뮤니티에 처음 기여하며 마주한 #6680 패치 — WAL 구조의 기본부터 XLOG_SWITCH 반환값 일관성 문제, v1→v2 진화 과정과 메일 토론을 단계별로 따라가며 정리합니다.