토크나이저와 임베딩
분류: Layer 11 - AI 기초 & 머신러닝 | 선수지식: L11-10 (ML 수학 토대), L11-50 (트랜스포머)
토크나이저와 임베딩 — BPE, 임베딩 공간, 의미 거리
섹션 제목: “토크나이저와 임베딩 — BPE, 임베딩 공간, 의미 거리”1. 한 줄 정의
섹션 제목: “1. 한 줄 정의”토크나이저는 텍스트를 모델이 처리하는 토큰 ID 시퀀스로 쪼개는 모듈이고, 임베딩은 토큰·문장·이미지를 의미를 보존하는 고차원 벡터로 변환하는 모델이다. LLM 비용·다국어 효율·검색 성능의 토대.
2. 왜 중요한가
섹션 제목: “2. 왜 중요한가”- LLM 비용 직관의 토대: API 가격이 토큰 단위 → “한국어가 영어보다 더 비싼 이유”가 토크나이저 안에 있다
- Context window 활용: 같은 글을 적은 토큰으로 표현하면 더 긴 컨텍스트 가능
- 임베딩 = RAG·검색의 토대 (L12-30): 의미 거리가 검색 품질을 결정
- Matryoshka·차원 축소: vector store 비용을 4~8배 줄이는 토대
- fine-tuning 시 토크나이저 일관성: 잘못 다루면 학습 실패하는 silent failure 영역
2.5 Lineage — word-level OOV와 word2vec polysemy가 만든 토픽
섹션 제목: “2.5 Lineage — word-level OOV와 word2vec polysemy가 만든 토픽”frontmatter lineage_oneliner: "토큰화 OOV 문제를 BPE로 해결하고 임베딩으로 의미거리 기반 검색 지원"의 본문 근거.
토크나이저 계보 — word-level → BPE → byte-level BPE
섹션 제목: “토크나이저 계보 — word-level → BPE → byte-level BPE”- Word-level의 한계: 단어 단위 vocab은 어휘가 폭증하고, 학습 코퍼스에 없던 단어를
[UNK]로 떨어뜨린다. 대규모 코퍼스에서는 unique unicode 문자만으로 ~5K가 일반 32K BPE vocab의 상당 비중을 차지한다 (openai/gpt-2 encoder.pybytes_to_unicode()주석). 신조어·고유명사가 등장할 때마다 vocab 재학습이 필요. - BPE 등장 (Sennrich et al. 2015): subword 합병으로 어휘를 고정한 채 새 단어를 토큰 조합으로 표현. WMT15 EN→DE에서 dictionary back-off 대비 +1.1 BLEU, EN→RU +1.3 BLEU (arXiv:1508.07909). 단 base 문자가 vocab에 없으면 여전히 OOV.
- Byte-level BPE (Radford et al. 2019, GPT-2): base vocab을 256 byte로 고정해 모든 unicode를 UTF-8 byte 시퀀스로 표현 → OOV가 원천 제거. GPT-2 50,257 vocab, GPT-4o
200k vocab(§3.3)이 모두 이 흐름. → §3.1§3.4의 BPE 변형 표가 이 계보 위에 있다.
임베딩 계보 — 정적 단일 vector → contextual encoder → contrastive sentence encoder
섹션 제목: “임베딩 계보 — 정적 단일 vector → contextual encoder → contrastive sentence encoder”- word2vec/GloVe (2013~2014)의 한계: 한 단어 = 단일 vector. “bank”(은행/강둑) 같은 polysemy를 두 의미가 한 좌표에 뒤섞인 채 표현 → 의미 다른 두 문장 거리가 비슷하게 나오는 silent failure (Stanford SAIL — How Contextual are Contextualized Word Representations?). OOV 단어도 별도 처리 필요.
- Contextual embedding (BERT 2018, transformer encoder): 각 토큰 vector가 self-attention으로 문맥마다 달라짐 → §3.5의 “token embedding = LLM의 first layer”는 정적 vector를 attention으로 일반화한 결과. polysemy 해소되지만 토큰 단위라 문장 검색에는 풀링이 필요.
- Contrastive sentence embedding (SimCSE/E5/BGE/voyage, 2021~2025): contextual encoder 위에 InfoNCE(§3.9)를 얹어 문장 단위 vector를 학습 → §3.8의 모델 표가 이 흐름의 결과.
선수지식 연결
섹션 제목: “선수지식 연결”- L11-10 (ML 수학 토대): 내적·norm·cosine 정의가 §3.7 의미 거리의 토대. 이 정의가 없으면 §3.10 MRL·§3.11 quantization이 “왜 차원을 줄여도 의미가 보존되나”를 설명할 수 없다.
- L11-50 (transformer & attention): self-attention이 polysemy를 푸는 정확한 메커니즘 — 이 토픽의 contextual·sentence embedding은 모두 transformer encoder 위에 contrastive head를 얹은 구조다.
이 토픽이 사라지면 LLM API 비용 견적·context window 실효 활용·RAG 검색 품질·다국어 처리 결정의 토대가 비어버린다. 한국어 토큰 비용 2~3× 차이(§3.3)도 byte-level BPE 계보를 모르면 “왜?”에 답할 수 없다.
3. 핵심 개념
섹션 제목: “3. 핵심 개념”3.1 토크나이저의 종류
섹션 제목: “3.1 토크나이저의 종류”§2.5에서 본 word-level → BPE → byte-level BPE 계보를 구현 단위로 펼치면 다음과 같다. 표 안의 BPE/SentencePiece/WordPiece는 모두 subword 합병 계열이고, 행 순서가 OOV·어휘 폭증을 풀어 가는 시간 순서다.
| 종류 | 예시 | 특징 |
|---|---|---|
| Word-level | 옛 NLP | 어휘 폭증, OOV 문제 |
| Character-level | byte-level | 어휘 작음, 시퀀스 매우 김 |
| BPE | GPT, LLaMA, Mistral | 빈도 높은 byte 쌍을 반복 합병. 균형 |
| SentencePiece | T5, ALBERT, mT5 | unicode 직접 처리, 언어 독립. BPE/Unigram 둘 다 지원 |
| WordPiece | BERT, DistilBERT | likelihood 기반 합병. ## 접두로 sub-token 표시 |
| Tiktoken | OpenAI GPT-3.5/4/o | OpenAI의 BPE 구현. byte-level + regex pretokenization |
현대 LLM 표준은 byte-level BPE — 모든 unicode를 처리할 수 있고 OOV가 없음.
3.2 BPE 알고리즘
섹션 제목: “3.2 BPE 알고리즘”1. 초기 어휘 = 모든 byte (256개)2. 코퍼스에서 가장 자주 나오는 byte 쌍 (a, b)를 찾는다3. 새 토큰 ab를 어휘에 추가, 코퍼스의 (a, b)를 ab로 치환4. 어휘 크기가 목표(예: 32k, 100k, 200k)에 도달할 때까지 반복예시 (영어):
"running"→["run", "ning"]또는["runn", "ing"](학습된 합병에 따라)
Llama 3 토크나이저: 128k vocabulary (Llama 2의 32k에서 4× 확대) — 더 많은 합병으로 토큰 효율 ↑.
3.3 토큰 비용과 다국어 효율
섹션 제목: “3.3 토큰 비용과 다국어 효율”토큰 수 = LLM API 비용. 토큰화 효율은 언어마다 크게 다르다.
| 언어 | 모델 | 영어 대비 비효율 | 비고 |
|---|---|---|---|
| 한국어 | GPT-4 (cl100k_base) | 2.5~3× | “안녕하세요, 세계!” ≈ 10~13 토큰 |
| 한국어 | GPT-4o (o200k_base) | 1.5~2× | 다국어 vocab 200k로 2× 확대 → 한국어 개선 |
| 한국어 | Llama 3 (tiktoken) | Llama 2 대비 평균 ~15% 토큰 절감 | |
| 일본어 | GPT-4 | ~2× | |
| 중국어 | GPT-4 | ~1.5× | 한 글자 정보 밀도 ↑ |
한국어가 비싼 이유:
- BPE가 영어 코퍼스 기반으로 학습 → 한국어는 byte 단위로 쪼개짐 (한 글자 ≈ UTF-8 3 bytes)
- vocab 크기가 작을수록 한국어가 더 많이 쪼개짐 (cl100k 100k vs o200k 200k)
- Llama 3는 tiktoken 계열로 전환 (Llama 2의 SentencePiece에서 변경) → 효율 개선
- 운영 시 영향: 같은 8k context window이라도 한국어로는
35k token 분량 글만 들어감 (모델 vocab에 따라)
직접 측정 — 한국어/영어 토큰 효율 (출처: openai/tiktoken):
# pip install tiktokenimport tiktoken
ko = "안녕하세요, 세계!"en = "Hello, world!"
for name in ("cl100k_base", "o200k_base"): # GPT-4 / GPT-4o 계열 enc = tiktoken.get_encoding(name) ko_tok = len(enc.encode(ko)) en_tok = len(enc.encode(en)) print(f"[{name:13}] KO={ko_tok:2}t EN={en_tok}t ratio={ko_tok/en_tok:.2f}x")예상 출력:
[cl100k_base ] KO=11t EN=4t ratio=2.75x ← GPT-4: 한국어 ~2.75배 비효율[o200k_base ] KO= 7t EN=4t ratio=1.75x ← GPT-4o: vocab 200k로 개선다음 단계: 같은 문장을 두 모델로 실제 호출해 청구 토큰 수와 비교. 차이가 1 이상이면 prompt 끝 trailing space·special token 누출을 §3.4로 점검. ratio가 위 값과 크게 다르면 텍스트의 한자/이모지 비율을 의심.
3.4 토크나이저의 silent failure
섹션 제목: “3.4 토크나이저의 silent failure”운영자가 가장 자주 만나는 함정.
- 공백 처리 차이: GPT-4는
" hello"와"hello"가 다른 토큰. prompt 끝의 trailing space가 모델 출력 확률을 바꿈 - Special tokens:
<|im_start|>,<|endoftext|>같은 chat template 토큰. raw text와 섞이면 prompt injection 위험 또는 모델 혼란 - Tokenizer mismatch: fine-tuning 시 base와 다른 토크나이저로 학습 → 학습은 되지만 추론 결과 망가짐
- Numbers: 숫자가 일관 없이 쪼개짐.
"1000"vs"1001"이 다른 토큰화 → 산수 약함의 출처 - Emoji·이모지·복잡 unicode: 토큰 여러 개로 쪼개져 비싸짐
3.5 임베딩의 정의
섹션 제목: “3.5 임베딩의 정의”토큰 또는 문장을 고차원 벡터로 변환하는 함수.
- Token embedding: LLM 내부의 first layer. 각 token ID → vector. word2vec의 정적 단일 vector를 self-attention으로 문맥별 vector로 일반화한 산물(§2.5) — 같은 토큰 “bank”라도 layer 통과 후 vector가 문맥마다 다르다.
- Sentence embedding: 문장 전체 → 단일 vector (검색·분류용). contextual encoder 출력을 풀링하고 §3.9 contrastive 학습으로 다듬은 결과.
- Image embedding: 이미지 → vector (CLIP)
- Cross-modal: 텍스트와 이미지가 같은 공간에 임베딩 (CLIP, multimodal models)
3.6 임베딩 공간의 성질
섹션 제목: “3.6 임베딩 공간의 성질”훌륭한 임베딩의 특징:
- 의미가 거리: 비슷한 의미 → 가까운 거리
- 연산 가능:
king - man + woman ≈ queen(word2vec) — 현대 LLM 임베딩에선 약하지만 직관 토대 - 클러스터 구조: 같은 토픽의 문서들이 군집 형성
- anisotropy 위험: 모든 임베딩이 좁은 cone에 몰리면 거리가 의미를 잃음 → contrastive learning이 이를 완화
3.7 의미 거리
섹션 제목: “3.7 의미 거리”| 거리 | 식 | 사용 |
|---|---|---|
| Cosine similarity | (a · b) / (||a|| ||b||) | 방향만 — RAG·검색 표준 |
| Euclidean | ||a - b||_2 | 크기까지 — 거의 안 씀 (anisotropy 영향) |
| Dot product | a · b | 정규화된 임베딩에서는 cosine과 같음 |
| Inner product | dot product의 일반 | FAISS·pgvector 인덱스 옵션 |
LLM 임베딩 모델은 보통 L2 정규화된 출력 → cosine = dot product. 검색 시 dot product가 더 빠름.
3.8 임베딩 모델
섹션 제목: “3.8 임베딩 모델”| 모델 | 차원 | Context | MTEB | 특징 |
|---|---|---|---|---|
| OpenAI text-embedding-3-small | 1536 | 8k | 62.3 | 가성비. Matryoshka. $0.02/1M |
| OpenAI text-embedding-3-large | 3072 | 8k | 64.6 | OpenAI 생태계 default. Matryoshka. $0.13/1M |
| Cohere embed-v4 (2025) | up to 1536 | 128k | - | 다국어, 멀티모달, MRL |
| Voyage AI voyage-3-large (2025-01) | 1024 | 32k | top SOTA | 다국어 SOTA, MRL + int8/binary 네이티브 |
| BGE-M3 (2024-01) | 1024 | 8k | ~63 | open-source 다국어 표준. dense+sparse+ColBERT 모드 |
| NV-Embed-v2 (NVIDIA) | 4096 | 32k | 72.3 | Llama-3.1-8B 기반, decoder-as-encoder |
| Qwen3-Embedding-8B | 32~4096 (flex) | 32k | 70.6 | flexible dim, 다국어 강함 |
| Stella / GritLM / mxbai-embed | 다양 | 다양 | 60~67 | open-weight 경량 |
| Gemini Embedding 2 (Google) | 768~3072 | 8k+ | 65+ | Google 진영 |
2025+ 흐름: leaderboard 상위권은 이제 거의 다 open-weight + decoder-as-encoder (LLM 자체를 임베딩으로 사용 — E5-mistral, NV-Embed, GritLM). OpenAI 3-large는 “최고 품질”보다는 “OpenAI 생태계라면 default” 위치.
선택 기준:
- OpenAI 생태계:
text-embedding-3-small(비용) /3-large(품질) - 다국어 SOTA:
voyage-3-large또는Qwen3-Embedding - on-prem·open:
BGE-M3(dense+sparse+ColBERT 통합) 또는NV-Embed-v2 - 한국어 특화:
BGE-M3기반 fine-tune 모델, KoSimCSE, ko-sroberta
3.9 임베딩 학습 — Contrastive Learning
섹션 제목: “3.9 임베딩 학습 — Contrastive Learning”같은 의미의 두 문장은 가깝게, 다른 의미는 멀게 학습.
Loss(InfoNCE) = -log[exp(sim(a, p)/τ) / Σ_n exp(sim(a, n)/τ)]
a: anchor (query 또는 문서)p: positive (a와 의미가 같은 것)n: negative (의미가 다른 것)τ: temperature- 자기지도학습(L11-30 §3.4)의 한 형태
- positive 쌍 만들기: 번역(대응 문장), paraphrase, query-document 매칭
- hard negative mining: 표면적으로 비슷하지만 의미 다른 negative가 학습 효과 ↑
- SimCSE, GTR, E5, BGE 모두 이 방식의 변형
3.10 Matryoshka Representation Learning (MRL)
섹션 제목: “3.10 Matryoshka Representation Learning (MRL)”차원을 사후 잘라도 의미가 보존되도록 학습.
일반 임베딩: 1536차원 vector를 그대로 사용Matryoshka: 256, 512, 768, 1024, 1536 모든 절단점에서 검색 품질 유지- OpenAI
text-embedding-3-large:dimensions파라미터로 256~3072 자유 선택. 256d로 절단해도 MTEB 평균이 ada-002(1536d, MTEB 61.0)를 상회 — 3-large 풀(3072d) MTEB 64.6, 256d 절단 시에도 ada-002 1536d를 넘는다 (OpenAI 공식 공지) - Cohere embed-v4 (2025): MRL + 멀티모달
- voyage-3-large: 1024 기본, 절단 가능
- 운영 가치: 같은 모델로 vector store storage·메모리를 4
6× 절감, 검색 품질 손실은 13% 정도
3.11 차원 축소 vs Matryoshka
섹션 제목: “3.11 차원 축소 vs Matryoshka”- PCA·UMAP (사후): 임베딩을 별도 처리. 일부 정보 손실
- Matryoshka (사전): 학습 시 절단을 가정 → 절단해도 손실 적음
- Quantization 실전 수치 (Cohere/Voyage 보고):
fp32 → int8: 메모리 4× 절감, 검색 품질 거의 100% 보존fp32 → binary(1비트): 메모리 32× 절감, 속도 ~40× ↑, 품질 ~95% 유지- Matryoshka × Binary 결합: 256차원 + binary = 원본 대비 storage 192× 절감 가능
- Product Quantization (PQ): FAISS의 표준. 벡터를 chunk별 codebook으로 압축
3.12 Reranker — 2단계 검색
섹션 제목: “3.12 Reranker — 2단계 검색”bi-encoder 임베딩만으로는 RAG 품질의 한계가 있다. 2단계 검색이 표준.
Stage 1 (retrieve): bi-encoder 임베딩으로 top-100 후보 검색 (빠름)Stage 2 (rerank): cross-encoder reranker로 top-100을 top-10으로 재정렬 (정확)- cross-encoder: query·document를 같이 입력해 직접 점수. 정확하지만 매번 forward 필요 → 100개에만 적용
- 운영 표준 reranker:
BGE-reranker-v2-m3(open, 다국어)voyage-rerank-2/voyage-rerank-2-lite(API)Cohere Rerank 3.5(API)
- 한국어 RAG에서 ROI 가장 큰 도구 — recall@10이 보통 10~30% 개선
3.13 Hybrid Search & Sparse Embedding
섹션 제목: “3.13 Hybrid Search & Sparse Embedding”Dense embedding만으로는 약한 영역(고유명사·신조어·법률·코드 식별자) 보완.
- Hybrid search: BM25(lexical) + dense embedding(semantic) 결과를 RRF(Reciprocal Rank Fusion)로 결합
- Sparse / learned-sparse embedding: SPLADE — 어휘 기반이지만 학습된 가중치. BM25보다 강하고 dense보다 해석 가능
- BGE-M3의 통합 모드: 한 모델이 dense + sparse + ColBERT(multi-vector late interaction) 출력. 셋을 RRF로 결합하면 단일 dense 대비 큰 개선
- 한국어 운영: 고유명사·법령·약어 비중이 크면 BM25/sparse 가중치를 dense보다 높이는 게 흔히 정답
3.14 Embedding의 한계
섹션 제목: “3.14 Embedding의 한계”- 표현 압축: 긴 문서를 한 vector로 압축 → 세부 정보 손실
- anisotropy: 모든 임베딩이 좁은 cone에 몰림. cosine이 의미를 충분히 구분 못 할 때
- OOD: 학습 코퍼스 밖 도메인은 품질 폭락 (의학·법률 등)
- 고유명사·신조어: BPE 토크나이저가 잘못 쪼개면 임베딩도 실패
- 검색 vs 생성: 검색에 좋은 임베딩 ≠ 생성 모델 내부 임베딩 (역할 다름)
3.15 깨지는 조건 정량 표 (운영 결정용)
섹션 제목: “3.15 깨지는 조건 정량 표 (운영 결정용)”| 기법 | 효과 발휘 범위 | 깨지는 조건 |
|---|---|---|
| Dense embedding only | 일반 자연어 QA | 고유명사·법률·코드·신조어 多 → BM25 가중치 ↑ |
| BM25 only | 키워드 정확 매칭 | paraphrase·의미 검색 → dense 보강 필요 |
| Hybrid (RRF k=60) | 일반 도메인 | 고유명사 압도 도메인 → α 0.4:0.6 (BM25 우위) |
| Reranker | top-100 → top-10 재정렬 | top-10 이미 정확하면 50~100ms 추가 손해 |
| Matryoshka 256d | 검색 quality 1~3% 손실 | 256d 미만은 품질 폭락 (절단 한계) |
| int8 quantization | 4× storage ↓, 품질 ~100% | 작은 모델·짧은 차원에선 효과 미미 |
| Binary embedding | 32× storage·40× 속도 | 단독 사용 품질 ~95% — fp32 rerank 필수 |
| KoSimCSE·BGE-M3-ko | 한국어 전용 도메인 | 다국어 cross-lingual 검색엔 다국어 모델 우위 |
3.16 Silent Failure 시나리오와 복구
섹션 제목: “3.16 Silent Failure 시나리오와 복구”| 증상 | 정량 시그널 | 원인 | 복구 |
|---|---|---|---|
| 한국어 query 검색 부정확 | recall@10 < 50% | 영어 임베딩 모델 사용 | 다국어 모델(BGE-M3, voyage-3-large)로 교체 |
| 고유명사 검색 실패 | exact match 점수 0% | dense만 사용 | hybrid (BM25 + dense + RRF) |
| Embedding API 결과 다름 | cosine sim 변화 0.3+ | 모델 버전 변경 | reindex 또는 dual-index 운영 |
| MRL 절단 후 품질 폭락 | recall@10 30%+ ↓ | MRL 미지원 모델 | OpenAI 3-small/large, voyage-3, Cohere v4로 |
| Token 비용 폭증 (한국어) | 토큰/요청 영어 대비 3×+ | 옛 토크나이저 사용 (cl100k) | o200k 모델 또는 GPT-4o로 교체 |
| Special token 누출 | 응답에 <|im_start|> 포함 | sanitize 누락 | input/output filter 적용 |
| Tokenizer mismatch (fine-tune) | 추론 결과 깨짐 | base와 다른 토크나이저 사용 | base 모델의 tokenizer/template 일관 사용 |
모델 버전 변경 시 reindex 결정 절차 (구체): OpenAI는 text-embedding-ada-002를 2025-01-04 deprecation 공지 → 2025-06-14 retire로 12개월 grace를 줬다 (OpenAI deprecations). 같은 query에 대해 ada-002·3-small 좌표계가 cosine 0.3+ 차이 → rolling migration 중 부분 색인된 인덱스는 retrieval 결과가 비결정적으로 흔들린다. 안전한 절차:
- dual-write: 새 인덱스를 만들고 양쪽 모델로 같은 문서를 동시에 인덱싱 (production traffic은 여전히 옛 인덱스)
- backfill: 기존 문서를 새 모델로 batch reindex. 진행률 90%+ 도달 전엔 cutover 금지
- shadow read: 같은 query를 양쪽에 보내
recall@10·top-1 일치율을 측정. 새 인덱스가 baseline 이상일 때만 다음 단계 - traffic switch: 100% cutover 후 1~2주 옛 인덱스를 read-only로 보존 (롤백 대비)
- purge: 사용자 캐시·로그에 남은 옛 vector 참조를 만료시킨 뒤에 옛 인덱스 삭제
dual-index 없이 in-place로 reindex하면 진행 중 query 결과가 “옛 vector vs 새 vector”가 섞여 신호와 노이즈를 구분할 수 없다. dimension이 다른 모델 간 마이그레이션은 더 까다로움 — ada-002(1536d) ↔ 3-large(3072d)는 storage·index 스키마 자체가 다르다.
3.17 임베딩의 일반 매핑 (Transferable Pattern)
섹션 제목: “3.17 임베딩의 일반 매핑 (Transferable Pattern)”임베딩의 핵심 — “고차원 공간에 의미 좌표 + 거리로 유사도” — 는 다른 시스템에서도 반복.
| 임베딩 구성요소 | 일반 시스템 매핑 |
|---|---|
| Vector (의미 좌표) | DB row, document, user profile, hash code |
| Distance (cosine, Euclidean) | DB join condition, similarity score |
| ANN index (HNSW) | DB index (B-tree, LSM-tree), cache key index |
| Quantization (int8, binary) | columnar compression, bloom filter |
| Matryoshka (사전 절단) | hierarchical index, summary-detail trade-off |
| Hybrid (BM25 + dense) | full-text + structured query (Postgres + tsvector) |
| Reranker (cross-encoder) | 2-stage cache lookup, allowlist + verification |
일반 공식: “근사 검색 + 정확 재정렬”의 2단계 패턴이 검색 시스템 전반에 있다. 임베딩은 데이터를 의미 공간으로 옮기는 도구이고, 그 위의 모든 검색은 “거리·랭킹·재정렬”의 표준 토대를 따른다.
새 검색·임베딩 기술 만났을 때 5가지 자가 질문 — 위 매핑을 실제로 적용하려면 무엇을 먼저 보는가. §4 운영 시나리오는 이 5질문을 직접 적용한 결정이다.
- 표현 단위·dtype: vector 차원·정규화 여부·fp32/int8/binary 중 무엇? — 인덱스(HNSW/IVF) 선택과 storage 비용을 결정
- 거리 정의: cosine / dot / Euclidean / 다중 모드(RRF) 중 무엇? — 정규화 필요 여부와 후처리 비용을 결정
- 2-stage 가능 여부: bi-encoder retrieve + cross-encoder rerank가 가능한가? — top-100 안에 정답이 들어오는지(recall@100) 먼저 확인하지 않으면 rerank를 추가해도 무의미
- 압축의 native 지원: MRL·quantization을 모델 학습 단계에서 지원하나, 사후 PCA를 강제하나? — native면 손실 1
5%, 사후만 가능하면 1030% 손실 가능 - Silent failure 측정 지표: recall@10·exact match·cosine drift 중 1개 이상을 baseline으로 정해뒀나? — 정의 없으면 OOD·버전 drift·tokenizer mismatch를 운영 중에 못 본다
4. 실무에서 어디에 쓰이나
섹션 제목: “4. 실무에서 어디에 쓰이나”- LLM API 비용 견적 (입력 토큰 추정)
- RAG·의미 검색 (L12-30)
- 클러스터링·토픽 모델링
- 추천 시스템 (사용자·아이템 임베딩)
- 분류 baseline (임베딩 + LR, L11-20 §5)
- 다국어 검색 (cross-lingual)
- 코드 검색 (Voyage code, code embedding)
운영 시나리오 — 한국어 RAG 임베딩 모델 결정 (§3.17 5질문 적용)
섹션 제목: “운영 시나리오 — 한국어 RAG 임베딩 모델 결정 (§3.17 5질문 적용)”상황: 사내 한국어 문서 1M개, 검색 P95 < 100ms, recall@10 > 0.7
5질문을 단계로 적용: Q1 단위·dtype : 1024d vector (BGE-M3) → 256d × binary 절단 검토 Q2 거리 정의 : dense cosine + sparse + ColBERT를 RRF로 결합 (BGE-M3 멀티모드) Q3 2-stage : bi-encoder retrieve(top-100) + bge-reranker-v2-m3 cross-encoder Q4 압축 native: BGE-M3는 MRL/multi-mode 학습 단계에서 지원 Q5 SF 지표 : recall@10 < 0.5 → hybrid 가중치 재조정, exact match 0% → BM25 가중치 ↑
선택지: A. text-embedding-3-large (3072d, OpenAI): - 비용: $0.13/1M tokens, 1M docs ≈ $1300 - 한국어 OK, 다국어 다소 약함 - storage: 12GB (fp32) B. BGE-M3 (1024d, self-host): - 비용: GPU 호스팅 $200/월 - 한국어 강함 (한국어 fine-tune 모델 다수) - storage: 4GB (fp32) C. voyage-3-large (1024d, 2025 SOTA): - 비용: $0.18/1M, 다국어 SOTA - storage: 4GB (fp32) D. B + Matryoshka 256d + binary: - storage: 4GB / (4 × 32) = 32MB → 192× 절감
선택: D (BGE-M3 + MRL 256d + binary + 2-stage rerank).대안 비선택: A는 다국어 약함, C는 비용 변동, B 단독은 storage 비효율.기대치 (사내 측정 전, 외부 공식 벤치 근거):
- storage 32MB: fp32→binary 32× × MRL 256/1024 4× 절감 (Cohere int8/binary 보고)
- 품질 retention: binary 단독
9098% recall, fp32 rerank 결합 시99% (Cohere 보고, MIRACL 영어 기준; rescore multiplier 45 가정) - 다국어 retrieval: BGE-M3 dense+sparse+ColBERT RRF 결합 시 dense-only 대비 큰 폭 개선, MIRACL 18 언어 평균 nDCG@10 70.0 (BGE-M3 paper, arXiv:2402.03216)
사내 측정 책임 (실측 사례 부재 시 필수 절차):
위 수치는 외부 벤치(주로 영어 MIRACL) 추정이다. 한국어 사내 도메인은 OOD 가능. 도입 전 자체 검증셋 100~500쌍으로 recall@10·P95를 직접 측정하고, 외부 벤치와 1.5× 이상 어긋나면 Q5 SF 신호로 보고 모델/가중치를 재선택한다. 본 문서는 외부 벤치 측정만 인용하며, 사내 실측 사례는 측정 후 본 절을 갱신한다.
§3.3 한국어 토큰 효율 + §3.8 모델 선택 + §3.10 MRL + §3.11 binary + §3.15 깨지는 조건 모두 적용.
5. 현재 내 업무와 연결점
섹션 제목: “5. 현재 내 업무와 연결점”플랫폼 엔지니어가 LLM 운영할 때 토크나이저·임베딩 직관이 다음에 도움 된다.
- 한국어 비용 견적: 영어 대비 1.5~2× 토큰 비효율 → context window 실효 활용도 절반. prompt 설계 시 영어 작성이 비용 절감 가능
- 임베딩 모델 선택:
text-embedding-3-large(품질) vstext-embedding-3-small(비용) vs BGE(self-host) 결정. 도메인이 영어면 small도 충분, 다국어면 Cohere - vector store 비용: Matryoshka로 1536→512 절단하면 storage·메모리 3× 절감, 검색 품질은 거의 유지
- fine-tuning 시 토크나이저 정합성: base 모델의 토크나이저를 그대로 사용하지 않으면 학습은 되지만 추론 망가짐 — silent failure
- prompt injection 방어: special token (
<|im_start|>등)을 user input에서 sanitize
6. 자주 헷갈리는 개념 비교
섹션 제목: “6. 자주 헷갈리는 개념 비교”| 개념 A | 개념 B | 차이점 |
|---|---|---|
| Word-level | BPE | OOV 문제 vs subword 합병으로 해결 |
| BPE | SentencePiece | byte 기준 vs unicode 기준 (언어 독립) |
| WordPiece | BPE | likelihood 기반 vs 빈도 기반 |
| Token embedding | Sentence embedding | LLM 내부 first layer vs 검색용 단일 vector |
| Cosine similarity | Euclidean | 방향 vs 거리. 정규화된 임베딩에선 cosine 표준 |
| PCA | Matryoshka | 사후 차원 축소 vs 학습 시 차원별 의미 정렬 |
| Float32 | Binary embedding | 표현력 vs 32× 메모리 절감 |
| Token | Character | byte/subword 단위 vs 글자 단위 |
| Tiktoken | HuggingFace tokenizer | OpenAI 표준 vs open-source 다양 (transformers 라이브러리) |
7. 체크리스트
섹션 제목: “7. 체크리스트”- BPE 알고리즘을 한국어 토큰 효율 관점에서 설명할 수 있다
- “한국어가 영어보다 1.5~2× 비싼” 이유를 byte-level BPE로 설명할 수 있다
- Cosine similarity 식과 의미를 L11-10의 내적 정의로 유도할 수 있다
- Matryoshka 임베딩이 차원 축소 비용을 줄이는 이유를 설명할 수 있다
- 임베딩 모델 선택 시 품질·비용·privacy·다국어 4축으로 결정할 수 있다
- Tokenizer mismatch가 silent failure를 일으키는 이유를 fine-tuning 관점에서 설명할 수 있다
- Contrastive learning과 InfoNCE의 직관 (가까운 것은 가깝게, 먼 것은 멀게)을 말할 수 있다
8. 추가 학습 키워드
섹션 제목: “8. 추가 학습 키워드”- 토크나이저: BPE, SentencePiece, WordPiece, Unigram, byte-level BPE, tiktoken, HuggingFace tokenizers
- 임베딩 모델: text-embedding-3, voyage, Cohere embed, BGE, gte, E5, Nomic, Snowflake Arctic
- 임베딩 학습: contrastive learning, InfoNCE, SimCSE, hard negative mining, instruction tuning for embeddings
- 차원·압축: Matryoshka, PCA, UMAP, Product Quantization, binary embedding, BinaryNet
- vector store: FAISS, pgvector, Pinecone, Weaviate, Qdrant, Milvus, ChromaDB
- 검색: BM25, hybrid search, reranking, ColBERT (late interaction)
9. 내가 직접 확인해볼 것
섹션 제목: “9. 내가 직접 확인해볼 것”토크나이저 비교
섹션 제목: “토크나이저 비교”- OpenAI tiktoken으로 같은 한국어/영어 문장을 토큰화 비교 — 자릿수 차이 직접 확인
- HuggingFace
transformers로 LLaMA-3 vs LLaMA-2 토크나이저로 한국어 토큰 수 비교 — Llama 3가 더 효율적 - OpenAI 토크나이저(
tiktoken.encoding_for_model("gpt-4"))에서" hello"vs"hello"토큰 ID 비교 — 다름 확인
임베딩 거리
섹션 제목: “임베딩 거리”-
text-embedding-3-small로 5개 단어(“개”, “고양이”, “비행기”, “기차”, “자동차”)를 임베딩 후 코사인 유사도 행렬 계산. “비행기-기차”가 “비행기-개”보다 가까운지 - 같은 문장을 영어로 번역해 임베딩 후 두 vector의 코사인 유사도 측정 — cross-lingual 모델은 0.7+ 나와야 함
Matryoshka
섹션 제목: “Matryoshka”-
text-embedding-3-large(3072)로 1000개 문서 임베딩. 256/512/1024/3072 차원으로 잘라 RAG retrieval recall@10 비교 — 256에서도 큰 손실 없는지
Silent failure 진단
섹션 제목: “Silent failure 진단”- HuggingFace로 fine-tune 후 추론에서 출력이 깨지는 경우 → tokenizer mismatch 점검 (
AutoTokenizer.from_pretrained경로) - LLM 출력에
<|im_start|>같은 special token이 보이면 → chat template 손상 의심
결과가 예상과 다를 때
섹션 제목: “결과가 예상과 다를 때”- 한국어 토큰 수가 예상보다 많음 → 모델별로 다름 (LLaMA-2는 매우 비효율, LLaMA-3는 개선). 모델 변경 검토
- 임베딩 검색 결과가 무관한 문서 반환 → anisotropy 또는 도메인 mismatch. reranker 도입 또는 도메인 fine-tune
- Matryoshka 절단 후 품질 폭락 → MRL 미지원 모델일 가능성. OpenAI text-embedding-3 또는 Cohere embed-v3 전용
10. 5줄 요약
섹션 제목: “10. 5줄 요약”- 토크나이저는 텍스트를 모델 입력 단위(토큰)로 쪼개고, 임베딩은 토큰·문장·이미지를 의미를 보존하는 고차원 벡터로 변환한다.
- Byte-level BPE가 LLM 표준이고, 한국어는 영어 대비 1.5~2× 토큰 비효율이라 비용이 더 든다.
- 임베딩 공간의 거리는 의미 거리이며, RAG·검색·추천의 토대다 (cosine similarity 표준).
- Matryoshka representation은 사후 차원 절단을 학습 시 가정해, vector store 비용을 4~6× 절감한다.
- Tokenizer mismatch, special token 누출, 한국어 토큰 효율 등이 운영 silent failure의 흔한 원인이다.
11. 출처
섹션 제목: “11. 출처”- Sennrich et al., Neural Machine Translation of Rare Words with Subword Units / BPE (arXiv:1508.07909)
- Kudo & Richardson, SentencePiece (arXiv:1808.06226)
- OpenAI, Tiktoken GitHub
- OpenAI, New embedding models and API updates (text-embedding-3)
- Kusupati et al., Matryoshka Representation Learning (arXiv:2205.13147)
- Gao et al., SimCSE (arXiv:2104.08821)
- Wang et al., E5 / Text Embeddings by Weakly-Supervised Contrastive Pre-training (arXiv:2212.03533)
- BAAI, BGE Embedding Models
- Cohere Embed v3 docs
- Voyage AI embedding models
- HuggingFace MTEB leaderboard
- Voyage AI — voyage-3-large announcement (2025)
- BAAI BGE-M3 — multi-functional, multi-lingual (arXiv:2402.03216)
- NVIDIA NV-Embed-v2
- Qwen3-Embedding
- Cohere — int8 / binary embeddings blog
- HuggingFace blog — Embedding Quantization
- GPT-4o tokenizer bias study (arXiv:2406.11214)
- BGE Reranker v2-m3
최종 수정: 2026-04-26