coredot.today
블로그로 돌아가기

#한국어 검색 스택

5개의 포스트

BM25는 한국어를 어떻게 쪼개나 — 조사·복합명사·영한 혼용, 토크나이저가 검색을 결정한다 (한국어 검색 스택 5편)
튜토리얼BM25한국어 토크나이저
2026.10.05

BM25는 한국어를 어떻게 쪼개나 — 조사·복합명사·영한 혼용, 토크나이저가 검색을 결정한다 (한국어 검색 스택 5편)

2편에서 BM25는 '약한 고리'였습니다. 왜 약했을까요. 이 글은 그 질문을 파고듭니다. 같은 문서, 같은 질문, 같은 BM25 공식에 토크나이저만 여덟 가지로 바꿔 보니 nDCG@10이 0.42에서 0.62까지 벌어졌습니다. 띄어쓰기로 자르면 '청년취업을'과 '청년취업'이 다른 단어가 되고, 형태소 분석기로 조사를 떼면 같은 단어가 되며, 글자 2-gram을 겹쳐 색인하면 사전에 없는 말까지 받아 줍니다. 한국어에서 어휘 검색이 어려운 세 가지 이유(교착어의 조사와 어미, 복합명사, 영한 혼용)를 예시 문장의 실제 토큰으로 보여 주고, 엘라스틱서치 nori의 decompound 모드와 불용 품사 기본값, Kiwi의 사용자 사전, BM25의 k1·b 다이얼을 실측으로 짚습니다. 결론은 BM25 자체가 약한 것이 아니라 한국어를 잘못 쪼갠 BM25가 약하다는 것입니다. 인터랙티브 4개와 삽화 8장.

코어닷투데이19분
4096차원에 HNSW가 필요한 이유 — 전수 비교의 벽, 차원의 저주, 그리고 그래프를 걸어서 찾는 법 (한국어 검색 스택 4편)
튜토리얼HNSW벡터 인덱스
2026.10.04

4096차원에 HNSW가 필요한 이유 — 전수 비교의 벽, 차원의 저주, 그리고 그래프를 걸어서 찾는 법 (한국어 검색 스택 4편)

1편에서 가장 좋았던 Qwen3-Embedding-8B는 문장 하나를 4,096개 숫자로 바꿉니다. 문서 589건이면 질문 하나에 589번 내적하면 되니 1초도 안 걸립니다. 그런데 문서가 5,000만 건이면? 같은 방식으로는 질문 하나에 2,000억 번 곱셈이고, 서버가 아무리 좋아도 초 단위입니다. 벡터 DB가 HNSW라는 인덱스를 쓰는 이유가 여기 있습니다. 이 글은 왜 고차원에서는 트리 인덱스가 소용없는지(차원의 저주), HNSW가 어떻게 스킵 리스트와 작은 세상 그래프를 합쳐 로그 시간에 근사 최근접을 찾는지, M·ef_construction·ef_search 세 손잡이가 무엇을 바꾸는지를 그림과 장난감 시뮬레이터로 풀고, 4,096차원 벡터 1만·10만·30만 개로 전수 비교와 hnswlib을 직접 재서 비교합니다. 10만 개에서 전수 비교 56ms 대 HNSW 1.3ms(재현율 0.98). 그리고 4,096차원의 진짜 병목은 그래프가 아니라 벡터 자체라는 것, 그래서 3편의 마트료시카 절단과 양자화가 HNSW와 곱해진다는 것을 메모리 계산기로 보입니다. 인터랙티브 4개와 삽화 8장.

코어닷투데이21분
마트료시카 임베딩 — 벡터를 앞에서부터 잘라도 되는 이유와, 잘랐을 때 실제로 남는 것 (한국어 검색 스택 3편)
튜토리얼마트료시카 임베딩Matryoshka Representation Learning
2026.10.03

마트료시카 임베딩 — 벡터를 앞에서부터 잘라도 되는 이유와, 잘랐을 때 실제로 남는 것 (한국어 검색 스택 3편)

Qwen3-Embedding-8B의 벡터는 숫자 4,096개입니다. 5,000만 청크를 float32로 저장하면 벡터만 819GB입니다. 그런데 이 벡터의 앞 256개만 남기고 나머지를 버려도 검색 품질의 93%가 남는다면? 그것이 마트료시카 임베딩입니다. 2022년 논문 「Matryoshka Representation Learning」이 제안하고 OpenAI text-embedding-3, Nomic v2, Qwen3 Embedding이 채택한 이 기법은 '중요한 정보를 벡터의 앞쪽에 몰아넣도록' 학습해, 러시아 인형처럼 큰 벡터 안에 작은 벡터가 들어 있게 만듭니다. 이 글은 원리를 장난감 모형으로 손에 잡히게 설명하고, 같은 한국어 코퍼스로 Qwen3 4B·8B와 Nomic v2를 32차원까지 잘라 가며 잰 실측 곡선, 저장 비용 계산기, 그리고 '짧게 걸러서 길게 고르는' 두 단계 적응형 검색이 전체 차원의 품질을 얼마나 되찾는지를 보여 줍니다. 인터랙티브 4개와 삽화 7장.

코어닷투데이20분
키워드와 의미, 둘 다 쓴다 — BM25·벡터·RRF·리랭커, 논문과 실측으로 보는 하이브리드 검색 (한국어 검색 스택 2편)
튜토리얼하이브리드 검색BM25
2026.10.02

키워드와 의미, 둘 다 쓴다 — BM25·벡터·RRF·리랭커, 논문과 실측으로 보는 하이브리드 검색 (한국어 검색 스택 2편)

원문 메모의 그림은 이랬습니다. BM25와 벡터 검색을 나란히 돌리고, 결과를 RRF로 합치고, 리랭커로 다시 고른다. 이 글은 그 그림의 각 칸을 논문과 실측으로 채웁니다. 2009년 SIGIR의 두 쪽짜리 논문이 제안한 RRF는 점수 대신 등수만 쓰는 단순한 공식인데 왜 통하는지, k=60은 어디서 왔는지, 2023년 TOIS 논문은 왜 '점수 융합이 RRF보다 낫다'고 했는지, 2025년의 '약한 고리' 발견은 무엇인지. 그리고 1편의 한국어 코퍼스로 직접 재 보니, 등가중 RRF는 벡터 단독보다 오히려 나빴고 이유는 BM25가 약한 고리였기 때문이었습니다. 반면 강한 임베딩 둘(Qwen3-8B + BGE-M3)을 RRF로 합치자 어느 쪽 단독보다 좋아졌습니다. 리랭커는 '따로 읽고 비교'하는 바이 인코더와 '같이 읽고 판정'하는 크로스 인코더의 차이로 풀고, 로컬 LLM을 리랭커로 써서 상위 10개의 순서가 얼마나 바뀌는지 잽니다. 인터랙티브 5개와 삽화 8장.

코어닷투데이34분
한국어 임베딩 모델, 우리 문서로 직접 재봤다 — Qwen3-Embedding 8B·4B·0.6B, BGE-M3, Nomic v2 MoE 실측 비교 (한국어 검색 스택 1편)
튜토리얼한국어 임베딩Qwen3-Embedding
2026.10.01

한국어 임베딩 모델, 우리 문서로 직접 재봤다 — Qwen3-Embedding 8B·4B·0.6B, BGE-M3, Nomic v2 MoE 실측 비교 (한국어 검색 스택 1편)

RAG를 만들 때 가장 먼저 부딪히는 질문이 '임베딩 모델은 뭘 쓰지?'입니다. 이 글은 그 질문에 남의 벤치마크가 아니라 우리 문서로 답합니다. 코어닷투데이 블로그와 뉴스 589건을 코퍼스로, 사람이 일부러 다른 말로 쓴 질문 22개와 로컬 LLM이 바꿔 쓴 질문 45개, 키워드 질문 18개를 만들고, 맥 한 대의 Ollama에서 Qwen3-Embedding 8B·4B·0.6B, BGE-M3, Nomic Embed v2 MoE 다섯 모델을 같은 조건으로 돌렸습니다. 임베딩이 무엇인지, 코사인 유사도가 왜 각도인지부터 시작해, '청년 일자리'라는 말이 없는 문서를 각 모델이 어떻게 찾는지 실제 값으로 보여 주고, 지시문 접두어 한 줄이 점수를 어떻게 바꾸는지, 같은 한국어 문서를 토크나이저가 얼마나 다르게 쪼개는지, 8B와 4B의 차이가 어디서 나는지를 따져 봅니다. 결론은 순위표 하나가 아니라 '어떤 환경에서 무엇을 고르나'이고, 인터랙티브 6개와 삽화 8장으로 함께 읽습니다. 2편은 BM25·RRF·리랭커, 3편은 마트료시카 임베딩입니다.

코어닷투데이32분