[PostgreSQL] Vector Search를 위한 인덱스 타입 비교 (HNSW vs IVFFlat)

2024. 11. 14. 21:35RDBMS

서론

안녕하세요! 요즘 AI 시대를 맞이하여 벡터 검색(Vector Search)이 정말 핫한데요. PostgreSQL에서도 pgvector 확장을 통해 벡터 검색을 지원하고 있습니다. 오늘은 벡터 검색에 사용되는 두 가지 주요 인덱스 타입인 HNSW와 IVFFlat에 대해 알아보겠습니다.

무엇이 다를까?

우선 두 인덱스의 주요 특징을 간단히 비교해볼까요?

HNSW (Hierarchical Navigable Small World)

  • 그래프 기반 인덱스
  • 빠른 검색 속도
  • 더 많은 메모리 사용
  • 인덱스 생성이 더 오래 걸림

IVFFlat (Inverted File Flat)

  • 클러스터 기반 인덱스
  • 적은 메모리 사용
  • 빠른 인덱스 생성
  • HNSW보다는 조금 느린 검색 속도

실제 사용 예제

간단한 예제로 두 인덱스의 사용법을 살펴보겠습니다.

-- pgvector 확장 설치
CREATE EXTENSION vector;

-- 테스트용 테이블 생성
CREATE TABLE documents (
    id SERIAL PRIMARY KEY,
    content TEXT,
    embedding vector(1536)  -- OpenAI의 embedding 차원
);

-- HNSW 인덱스 생성
CREATE INDEX hnsw_idx ON documents 
USING hnsw (embedding vector_cosine_ops)
WITH (m = 16, ef_construction = 64);

-- IVFFlat 인덱스 생성
CREATE INDEX ivf_idx ON documents 
USING ivfflat (embedding vector_cosine_ops)
WITH (lists = 100);

각 인덱스의 동작 원리

HNSW의 동작 방식

-- HNSW 검색 예제
SELECT content, 
       1 - (embedding <=> '[vector_values]') as similarity
FROM documents
ORDER BY embedding <=> '[vector_values]'
LIMIT 5;

HNSW는 다음과 같이 동작합니다:

  1. 계층적 그래프 구조 생성
  2. 상위 레이어에서 하위 레이어로 이동하며 검색
  3. 각 노드는 이웃 노드들과 연결

주요 파라미터:

  • m: 노드당 최대 이웃 수
  • ef_construction: 인덱스 생성 시 정확도

IVFFlat의 동작 방식

-- IVFFlat 검색 예제
SET ivfflat.probes = 10;  -- 검색할 클러스터 수 설정

SELECT content, 
       1 - (embedding <=> '[vector_values]') as similarity
FROM documents
ORDER BY embedding <=> '[vector_values]'
LIMIT 5;

IVFFlat은 다음과 같이 동작합니다:

  1. 데이터를 여러 클러스터로 분할
  2. 쿼리 벡터와 가장 가까운 클러스터 선택
  3. 선택된 클러스터 내에서 검색

주요 파라미터:

  • lists: 클러스터 수
  • probes: 검색할 클러스터 수

성능 비교

간단한 벤치마크 결과를 보여드리겠습니다:

-- 100만 개의 벡터에 대한 검색 성능 테스트
EXPLAIN ANALYZE
SELECT id, 1 - (embedding <=> '[vector_values]') as similarity
FROM documents
ORDER BY embedding <=> '[vector_values]'
LIMIT 10;

일반적인 성능 특성

  1. 검색 시간
    • HNSW: ~5-10ms
    • IVFFlat: ~20-30ms
  2. 메모리 사용량
    • HNSW: 원본 데이터의 약 50-100%
    • IVFFlat: 원본 데이터의 약 20-30%

어떤 상황에서 어떤 인덱스를 선택할까?

HNSW 선택 시기

  • 검색 속도가 최우선일 때
  • 메모리 자원이 충분할 때
  • 높은 정확도가 필요할 때
  • 실시간 검색이 필요할 때

IVFFlat 선택 시기

  • 메모리 사용량이 중요할 때
  • 빠른 인덱스 생성이 필요할 때
  • 약간의 검색 시간 증가를 감수할 수 있을 때
  • 대규모 데이터셋을 다룰 때

주의할 점

  1. 인덱스 생성 시간 고려하기
  2. 메모리 사용량 모니터링하기
  3. 정기적인 VACUUM ANALYZE 실행하기
  4. 적절한 파라미터 튜닝하기

마치며

저는 실제로 두 인덱스를 모두 적용한뒤 RAG 평가 도구를 사용해서 실제 검증후 사용하고 있습니다. 여러분도 적용과 함깨 RAG를 테스트하여 각 어플리케이션에 맞는 인덱스 선택이 필요하다고 생각합니다!

다음에는 벡터 검색의 성능 최적화 팁에 대해 다뤄보도록 하겠습니다. 감사합니다! 😊