Skip to main content
이 문서는 RAG 섹션의 일부입니다.
임베딩 기반 Dense 검색이 “의미”를 이해한다면, BM25는 “단어 자체”를 정확하게 매칭합니다. 제품번호, 오류 코드, 고유명사 검색에서 BM25는 여전히 Dense 검색을 압도합니다. 이 페이지에서는 TF-IDF부터 BM25까지의 발전 과정과 수식의 의미를 자연어로 풀어 설명합니다.

TF-IDF: BM25의 조상

BM25를 이해하려면 먼저 TF-IDF를 알아야 합니다. TF-IDF는 “단어의 중요도”를 두 가지 관점에서 측정합니다.

TF (Term Frequency) — “이 문서에서 얼마나 자주 나오는가?”

직관: 검색어가 문서에 많이 등장할수록 해당 문서가 그 주제에 관련될 가능성이 높습니다.

IDF (Inverse Document Frequency) — “전체에서 얼마나 드문가?”

직관: 모든 문서에 나오는 단어(“그리고”, “있다”, “the”)는 검색 가치가 낮습니다. 희소한 단어일수록 검색 판별력이 높습니다.

TF-IDF 점수

“Anomalib”이 3번 등장하는 문서: 3 × 9.90 = 29.7 (매우 높음) “데이터”가 10번 등장하는 문서: 10 × 0.22 = 2.2 (낮음)
참고 핵심 통찰: TF-IDF의 강력함은 IDF 부분 에 있습니다. 흔한 단어의 영향을 줄이고, 희소한(= 의미 있는) 단어의 영향을 극대화합니다.

TF-IDF의 한계

  1. 문서 길이 미보정: 10페이지 문서는 단순히 길기 때문에 단어가 더 많이 등장합니다. TF-IDF는 이를 보정하지 않아 긴 문서가 항상 유리합니다.
  2. 포화 효과 없음: “Databricks”가 3번 나온 문서와 300번 나온 문서의 점수 차이가 100배입니다. 하지만 실제로 3번이든 300번이든 관련성 차이는 크지 않습니다.

BM25: TF-IDF의 진화

BM25 (Best Matching 25)는 TF-IDF의 두 가지 한계를 우아하게 해결합니다.

BM25 수식

개선점 1: 포화 함수 (Saturation)

BM25는 TF가 증가해도 점수가 상한선에 수렴 합니다. 수식에서 이것이 어떻게 작동하는지 보면, TF 관련 부분은 TF × (k1 + 1) / (TF + k1) 형태입니다. TF가 아무리 커져도 분자의 TF와 분모의 TF가 함께 커지므로, 이 값은 (k1 + 1)이라는 상한에 수렴합니다. 이것은 x / (x + c) 형태의 포화 함수(saturation function) 로, x가 0일 때 0이고 x가 무한대일 때 1에 수렴하는 S자 곡선입니다:
이것은 “3번 나왔든 100번 나왔든, 이 문서가 해당 단어와 관련 있다는 신호는 비슷하다” 는 직관을 반영합니다. k1 파라미터의 역할:
  • k1이 작으면(0.5): 빠르게 포화 → TF 차이가 거의 무시됨
  • k1이 크면(3.0): 천천히 포화 → TF 차이가 더 반영됨

개선점 2: 문서 길이 정규화

b 파라미터의 역할:
  • b=0: 문서 길이를 완전히 무시
  • b=1: 문서 길이를 강하게 보정
  • b=0.75 (기본값): 적당한 수준의 보정
참고 수식을 자연어로 요약: BM25는 이렇게 말합니다: “이 단어가 문서에 나왔어? 좋아, 점수를 줄게. 많이 나왔어? 약간 더 줄게, 하지만 무한히 올라가진 않아. 그리고 이 문서가 너무 길어서 단어가 많이 나온 거라면, 좀 깎을게.”

Dense vs Sparse: 시나리오별 비교

주의 핵심: Dense와 BM25는 경쟁 관계가 아니라 보완 관계 입니다. 실무에서는 둘 다 사용하는 하이브리드 검색이 최선입니다.

한국어에서 BM25: 공백 분절의 한계

BM25는 텍스트를 단어 단위로 분리(토큰화) 해야 합니다. 영어는 공백으로 단어가 깔끔하게 나뉘지만, 한국어는 그렇지 않습니다.
“데이터브릭스에서”와 “데이터브릭스를”은 공백 분절 기준으로 다른 단어 가 됩니다. 이러면 “데이터브릭스”를 검색해도 매칭되지 않습니다.

해결: Kiwi 형태소 분석기

Kiwi 는 한국어 형태소 분석기(문장을 의미의 최소 단위인 형태소로 분리하는 도구)입니다. 내부적으로 통계 기반 모델과 사전을 결합하여, 조사/어미를 분리하고 원형(lemma)을 복원합니다. Python에서 pip install kiwipiepy로 설치할 수 있으며, C++ 기반이라 속도가 빠릅니다.
형태소 분석을 거치면 “데이터브릭스에서”, “데이터브릭스를”, “데이터브릭스의”가 모두 “데이터브릭스” 라는 동일한 토큰으로 정규화되므로, 조사 변화에 관계없이 정확한 키워드 매칭이 가능해집니다.
참고 실무 권장: 한국어 BM25를 구현할 때는 반드시 Kiwi 같은 형태소 분석기를 전처리로 적용하세요. 공백 분절만으로는 한국어 BM25의 성능이 영어 대비 30-50% 떨어집니다. 자세한 내용은 한국어 RAG 최적화를 참고하세요.

다음: Dense와 Sparse를 어떻게 결합할까요? → 하이브리드 검색 & RRF