0Pricing
SQL Academy · 강의

인덱스 전용 스캔과 가시성 맵

쿼리를 인덱스만으로 처리하도록 인덱스를 구성하고 가시성 맵을 최신 상태로 유지해 인덱스 전용 스캔을 활용해보세요.

인덱스 전용 스캔과 가시성 맵은(는) CoddyKit의 무료 SQL Academy 강의입니다. 이것은 4개 중 4번째 강의입니다. 아래에서 전체 강의를 무료로 읽을 수 있으며, 내장 코드 에디터와 24/7 AI 튜터와 함께 브라우저에서 직접 실습할 수 있습니다. 이 강의는 SQL Academy 학습 경로의 일부이며, 진행 상황이 웹과 CoddyKit 앱에 동기화됩니다. SQL Academy 강의에는 총 4개의 강의가 포함되어 있습니다.

인덱스 전용 스캔이란

일반적으로 인덱스 조회는 행 ID(TID)를 반환하며, 실제 행을 읽으려면 테이블을 방문해야 합니다. 인덱스 전용 스캔은 인덱스만 사용하여 쿼리에 답하므로 힙을 방문하지 않습니다. 훨씬 빠릅니다.

조건

인덱스 전용 스캔에는 다음이 필요합니다:

  • SELECT 대상인 모든 열이 인덱스에 포함되어야 합니다
  • 행이 있는 페이지가 가시성 맵에서 "모든 행이 표시됨"으로 표시되어야 합니다

가시성 맵

테이블의 각 페이지에 대한 비트맵입니다. 비트가 설정되어 있으면 해당 페이지의 모든 행이 모든 트랜잭션에 표시된다는 뜻입니다. VACUUM이 이를 유지 관리합니다. 가시성 맵이 없으면 PostgreSQL은 가시성을 확인하기 위해 힙을 방문해야 합니다.

쿼리를 인덱스 전용 스캔으로 만들기

필요한 모든 열을 포함합니다:

-- Query:
SELECT id, email FROM users WHERE id = 42;

-- Without an index on (id, email), only an Index Scan that visits the heap is possible.
-- With this:
CREATE INDEX users_id_email_idx ON users (id, email);
-- Or better:
CREATE INDEX users_id_email_idx ON users (id) INCLUDE (email);
-- The query can be index-only.

INCLUDE

키가 아닌 열을 포함하는 커버링 인덱스입니다(PG 11 이상). 열은 리프에 저장되지만 정렬에는 사용되지 않으므로 INSERT 비용에 영향을 주지 않습니다:

CREATE INDEX users_id_idx ON users(id) INCLUDE (email, full_name);

SELECT id, email, full_name FROM users WHERE id = 42;
-- Index-only scan if visibility map allows.

왜 여전히 힙을 방문할 수 있을까요

대량의 쓰기 작업 후에는 가시성 맵이 오래된 상태일 수 있습니다. FULL 없이 VACUUM을 실행하여 새로 고칩니다.

VACUUM (VERBOSE) users;
-- "scanned X pages, X of which are visible"
-- More visible pages = more Index-Only Scans possible.

인덱스 전용 스캔 확인

EXPLAIN으로 확인할 수 있습니다:

EXPLAIN ANALYZE
SELECT id, email FROM users WHERE id = 42;
--  Index Only Scan using users_id_email_idx on users
--    Index Cond: (id = 42)
--    Heap Fetches: 0       ← key number

Heap Fetches가 알려 주는 것

"Heap Fetches: 0" — 모든 데이터를 인덱스에서 가져온 완벽한 상태입니다. "Heap Fetches: N" — N개의 행에 힙 방문이 필요했다는 뜻입니다(가시성 맵 비트가 설정되지 않음). 자동 진공 처리가 실행되면 일반적으로 Heap Fetches가 줄어듭니다.

INCLUDE와 복합 인덱스 중 선택하기

  • SELECT만 하고 필터링이나 정렬에는 사용하지 않는 열에는 INCLUDE를 사용합니다
  • 열로 필터링하거나 정렬하기도 한다면 복합 키를 사용합니다

INCLUDE를 사용하면 인덱스 폭을 좁게 유지하면서 쓰기 속도도 높일 수 있습니다.

인덱스 비대화는 인덱스 전용 스캔을 방해합니다

비대한 인덱스에는 페이지가 더 많으므로 인덱스 전용 스캔에서도 더 많이 읽어야 합니다. 인덱스를 VACUUM 처리하고 비대화가 심해지면 인덱스를 재구성합니다.

모든 항목을 포함하지 마세요

인덱스에 열을 너무 많이 추가하면 쓰기가 느려지고 인덱스가 매우 커집니다. 자주 읽는 경로에 필요한 항목만 포함합니다.

커버로 사용하는 구체화된 뷰

특정 보고서의 읽기 속도를 극대화하려면 구체화된 뷰와 인덱스를 함께 사용하면 됩니다. 이는 임의의 계산 열을 포함할 수 있는 "커버링 인덱스"와 사실상 같습니다.

복습

인덱스 전용 스캔은 가장 빠른 읽기 경로입니다.

  • SELECT 대상인 모든 열이 인덱스에 포함되어야 합니다
  • INCLUDE를 사용하면 키가 아닌 열을 저렴하게 추가할 수 있습니다
  • 가시성 맵에 "모든 행이 표시됨"으로 표시되어야 하며 VACUUM이 최신 상태로 유지합니다
  • EXPLAIN에서 Heap Fetches: 0이 목표입니다

빠른 확인

인덱스 전용 스캔 노드인데도 EXPLAIN에 Heap Fetches: 100,000이 표시됩니다. 일반적인 해결 방법은 무엇인가요?

자주 묻는 질문

“인덱스 전용 스캔과 가시성 맵” 강의는 무료인가요?

네 — “인덱스 전용 스캔과 가시성 맵” 전체 내용을 이 웹사이트에서 무료로 읽을 수 있습니다. 인터랙티브하게 실습하려면(내장 코드 에디터와 24/7 AI 튜터), CoddyKit PRO로 업그레이드하면 SQL Academy 강의 전체를 잠금 해제할 수 있습니다. SQL Academy 강의에는 총 4개의 강의가 포함되어 있습니다.

“인덱스 전용 스캔과 가시성 맵”에서 뭘 배우나요?

쿼리를 인덱스만으로 처리하도록 인덱스를 구성하고 가시성 맵을 최신 상태로 유지해 인덱스 전용 스캔을 활용해보세요. 브라우저에서 직접 실행하는 실습 코드로 SQL Academy을(를) 배우며, 24/7 AI 튜터가 강의를 진행하면서 질문에 답변해줍니다.

SQL Academy을(를) 시작하는 데 경험이 필요한가요?

사전 경험은 필요하지 않습니다. CoddyKit의 SQL Academy은(는) 초급자부터 고급 학습자까지를 위해 구성되어 있으므로, 여기서 시작하거나 처음부터 시작할 수 있으며 자신의 속도대로 진행할 수 있습니다. 이것은 4개 중 4번째 강의입니다.

“인덱스 전용 스캔과 가시성 맵” 강의는 얼마나 걸리나요?

대부분의 CoddyKit 강의는 약 5~10분이 소요됩니다. 각 강의는 간결하고 인터랙티브하여 꾸준한 진행이 가능하며, 웹과 앱에서 중단한 부분부터 바로 시작할 수 있습니다.

이 SQL Academy 강의에서 코드를 작성하고 실행할 수 있나요?

네. 모든 SQL Academy 강의에는 내장 코드 에디터가 포함되어 있으므로, 브라우저에서 바로 실제 코드를 작성하고 실행한 후 즉시 AI 피드백을 받을 수 있습니다 — 로컬 설정이 필요 없습니다.

이 강의의 모든 강의

  1. MVCC와 비대화의 원인
  2. VACUUM, autovacuum, vacuum_cost_delay
  3. ANALYZE와 pg_statistic
  4. 인덱스 전용 스캔과 가시성 맵
← SQL Academy(으)로 돌아가기