🤖 AI/ML

BPE

Byte Pair Encoding

텍스트를 서브워드 단위로 토큰화하는 알고리즘. GPT 시리즈에서 사용.

📖 상세 설명

BPE(Byte Pair Encoding)는 텍스트를 서브워드(subword) 단위로 토큰화하는 알고리즘입니다. 자주 등장하는 문자 쌍을 반복적으로 병합하여 어휘를 구축하며, 단어 전체도 서브워드 조합도 모두 표현할 수 있어 OOV(Out-of-Vocabulary) 문제를 효과적으로 해결합니다.

원래 1994년 데이터 압축을 위해 Philip Gage가 개발했으나, 2015년 Sennrich 등이 Neural Machine Translation에 적용하면서 NLP 분야의 표준 토큰화 방법으로 자리잡았습니다. 이후 GPT 시리즈, BERT 등 대부분의 사전학습 모델이 BPE 변형을 채택했습니다.

알고리즘의 핵심은 빈도 기반 병합입니다. 초기에는 모든 문자를 개별 토큰으로 시작하고, 가장 빈번한 인접 토큰 쌍을 찾아 새로운 토큰으로 병합합니다. 이 과정을 원하는 어휘 크기에 도달할 때까지 반복하면, 자주 쓰이는 단어는 하나의 토큰으로, 드문 단어는 서브워드 조합으로 표현됩니다.

실무에서 BPE는 다국어 모델과 코드 생성에 특히 유용합니다. 새로운 언어나 전문 용어도 기존 서브워드로 분해되므로 완전히 모르는 단어가 발생하지 않습니다. GPT 토크나이저는 약 50,000개의 BPE 토큰을 사용하며, 한 영어 단어당 평균 1.3개의 토큰으로 분해됩니다.

💻 코드 예제

# BPE 토크나이저 학습 및 사용 예제
from tokenizers import Tokenizer
from tokenizers.models import BPE
from tokenizers.trainers import BpeTrainer
from tokenizers.pre_tokenizers import Whitespace

# 1. BPE 토크나이저 생성
tokenizer = Tokenizer(BPE(unk_token="[UNK]"))
tokenizer.pre_tokenizer = Whitespace()

# 2. 학습 데이터 준비
corpus = [
    "인공지능이 세상을 바꾸고 있습니다.",
    "머신러닝과 딥러닝은 인공지능의 핵심 기술입니다.",
    "자연어처리는 인공지능의 중요한 분야입니다.",
    "GPT는 자연어처리 모델의 대표적인 예입니다."
]

# 3. BPE 학습
trainer = BpeTrainer(
    vocab_size=1000,           # 어휘 크기
    special_tokens=["[UNK]", "[PAD]", "[CLS]", "[SEP]"],
    min_frequency=2            # 최소 빈도
)

# 파일에서 학습하는 것이 일반적이지만 예시로 직접 학습
tokenizer.train_from_iterator(corpus, trainer=trainer)

# 4. 토큰화 결과 확인
text = "인공지능은 미래의 핵심 기술이다"
output = tokenizer.encode(text)

print(f"원문: {text}")
print(f"토큰: {output.tokens}")
print(f"토큰 ID: {output.ids}")

# 5. Hugging Face GPT-2 토크나이저 사용 예
from transformers import GPT2Tokenizer

gpt2_tokenizer = GPT2Tokenizer.from_pretrained("gpt2")

english_text = "Artificial intelligence is transforming the world."
tokens = gpt2_tokenizer.tokenize(english_text)
ids = gpt2_tokenizer.encode(english_text)

print(f"\nGPT-2 토큰화:")
print(f"원문: {english_text}")
print(f"토큰: {tokens}")
print(f"토큰 수: {len(tokens)}")

🗣️ 실무 대화 예시

LLM 비용 최적화 논의에서

"API 비용이 토큰당 과금이니까 BPE가 어떻게 분해하는지 이해해야 해요. 영어는 효율적이지만 한국어는 같은 의미를 표현하는 데 2-3배 토큰이 필요합니다. 한국어 특화 토크나이저를 쓰거나, 프롬프트 압축 기법을 고려해봅시다."

커스텀 토크나이저 개발 중

"의료 도메인 데이터에 기본 BPE를 쓰면 전문 용어가 과도하게 분해돼요. 예를 들어 'acetaminophen'이 5-6개 토큰으로 쪼개지면 의미 파악이 어렵습니다. 도메인 코퍼스로 BPE를 새로 학습하거나 SentencePiece의 unigram 모델을 검토해보세요."

기술 면접에서

"BPE와 WordPiece의 차이는 병합 기준입니다. BPE는 가장 빈번한 쌍을 선택하고, WordPiece는 likelihood를 최대화하는 쌍을 선택합니다. SentencePiece는 언어 독립적으로 raw text에서 직접 학습할 수 있어서 다국어 모델에 더 적합합니다."

⚠️ 주의사항

1
토큰 수와 의미 단위 불일치

BPE는 빈도 기반이라 의미 단위와 토큰 경계가 일치하지 않습니다. 'unhappiness'가 'un', 'happiness'가 아니라 'unhapp', 'iness'로 분해될 수 있어, 형태소 분석이 중요한 태스크에서는 주의가 필요합니다.

2
어휘 크기 선택

어휘가 너무 작으면 모든 단어가 잘게 분해되어 시퀀스가 길어지고, 너무 크면 드문 토큰이 많아져 학습이 어렵습니다. 일반적으로 30K-50K가 적절하며, 도메인에 따라 조정이 필요합니다.

3
다국어 불균형

영어 중심 코퍼스로 학습된 BPE는 다른 언어를 비효율적으로 토큰화합니다. 한국어, 중국어, 일본어는 영어 대비 2-4배 많은 토큰을 사용하므로, 다국어 서비스에서는 균형 잡힌 학습 데이터가 필수입니다.

🔗 관련 용어

📚 더 배우기