본문으로 이동
메뉴 여닫기
환경 설정 메뉴 여닫기
개인 메뉴 여닫기
로그인하지 않음
지금 편집한다면 당신의 IP 주소가 공개될 수 있습니다.
Sentence embedding; 문장 임베딩
문장이나 문단 전체의 뜻을 고정 길이 벡터 하나로 나타낸 것, 또는 그 벡터를 만드는 기법

문장 임베딩(sentence embedding)은 문장, 문단, 짧은 문서를 수백~수천 차원의 실수 벡터 하나로 바꾼 것이다. 뜻이 비슷한 문장끼리 벡터 공간에서 가깝게 놓이도록 학습하므로, 두 문장의 유사도를 코사인 유사도 한 번으로 계산할 수 있다. 의미 검색, RAG의 문서 검색, 중복 질문 찾기, 군집화, 분류의 입력 특징으로 쓰인다.

단어 단위 벡터는 워드 임베딩, 텍스트 임베딩 전반의 종류와 활용은 텍스트 임베딩, 임베딩 모델 일반은 임베딩 모델 문서에 있다. 이 문서는 문장 하나를 벡터 하나로 만드는 구조(바이 인코더와 풀링), 학습 목표, 평가 방법, 실제 모델과 코드를 다룬다.

왜 BERT를 그대로 쓰지 않는가

편집 원본 편집

BERT 같은 사전 학습 인코더는 토큰마다 문맥 벡터를 내지만, 문장 벡터를 내도록 학습되지는 않았다. 두 문장의 관계를 판단하려면 두 문장을 한 입력으로 이어 붙여 넣는 교차 인코딩(cross-encoding)을 해야 한다. 이 방식은 정확하지만 문장 n개에서 가장 비슷한 쌍을 찾으려면 n(n-1)/2번 모델을 돌려야 한다. Sentence-BERT 논문은 문장 1만 개에서 가장 비슷한 쌍을 찾는 데 BERT로는 약 5천만 번의 추론, 약 65시간이 걸리지만 문장 임베딩으로는 약 5초면 된다고 계산했다.[1]

그렇다고 BERT 출력을 평균하거나 [CLS] 토큰 벡터를 그대로 쓰면 품질이 낮다. 같은 논문의 STS 평가(코사인 유사도와 정답 점수 사이의 스피어먼 상관, 7개 데이터셋 평균)에서 BERT 평균 벡터는 54.81, [CLS] 벡터는 29.19로, 2014년의 GloVe 단어 벡터 평균(61.32)보다도 낮았다. 미세 조정한 SBERT-NLI-base는 74.89였다.[1] 사전 학습 언어 모델의 표현은 모든 층에서 한쪽 방향으로 쏠려 있어(비등방성, anisotropy) 아무 두 문장이나 코사인 유사도가 높게 나오는 경향이 있다는 분석도 있다.[2]

구조: 바이 인코더와 풀링

편집 원본 편집

문장 임베딩 모델은 바이 인코더(bi-encoder) 구조다. 같은 인코더(가중치 공유, 샴 구조)가 두 문장을 따로 인코딩하고, 각 결과를 풀링해 벡터 u,v를 만든 뒤 유사도를 계산한다. 문서 쪽 벡터는 미리 계산해 벡터 데이터베이스에 넣어 둘 수 있으므로, 질의 때는 질의 하나만 인코딩하고 HNSW 같은 근사 최근접 이웃 색인으로 찾는다. 두 문장을 한 입력으로 넣는 크로스 인코더와의 비교는 리랭커 문서 참고.

풀링은 토큰 벡터 h1,…,hn을 벡터 하나로 줄이는 단계다.

방식 계산 쓰는 곳
평균 풀링(mean pooling) 패딩을 뺀 토큰 벡터의 평균 u=∑imihi∑imi (mi는 어텐션 마스크) SBERT 기본값. SBERT 논문의 비교에서 [CLS], 최댓값 풀링보다 대체로 나았다[1]
[CLS] 풀링 첫 토큰 벡터 u=h[CLS] BGE 계열, SimCSE
최댓값 풀링 차원별 최댓값 InferSent
마지막 토큰 풀링 마지막(EOS) 토큰 벡터 디코더 기반 대형 언어 모델을 임베딩 모델로 바꾼 경우(Qwen3-Embedding 등)

풀링 뒤에 L2 정규화를 하면 내적과 코사인 유사도가 같아져 색인과 계산이 단순해진다.

SBERT는 문장 쌍 데이터의 형태에 따라 세 가지 목표를 제시했다.[1]

  • 분류 목표: o=softmax(Wt[u;v;|u−v|])로 자연어 추론(NLI) 레이블(함의, 모순, 중립)을 맞힌다. 논문은 SNLI(57만 쌍)와 MultiNLI(43만 쌍)로 학습했고, 입력 조합 중 (u,v,|u−v|)가 가장 좋았다.
  • 회귀 목표: cos⁡(u,v)와 정답 유사도 점수의 평균 제곱 오차를 줄인다(STS 데이터).
  • 트리플렛 목표: max⁡(‖sa−sp‖−‖sa−sn‖+ϵ,0), 논문은 유클리드 거리와 ϵ=1을 썼다.

이후 표준이 된 것은 대조 학습이다. 질문-정답, 제목-본문, 함의 문장 쌍처럼 짝이 맞는 쌍을 모으고, 배치 안의 다른 문장을 음성으로 쓰는 InfoNCE 손실(sentence-transformers의 MultipleNegativesRankingLoss)로 학습한다.

  • SimCSE(2021): 비지도 판은 같은 문장을 드롭아웃만 바꿔 두 번 인코딩한 것을 양성 쌍으로 썼고, 지도 판은 NLI의 함의 문장을 양성, 모순 문장을 하드 네거티브로 썼다. BERT-base로 STS 평균 스피어먼 상관 76.3%(비지도), 81.6%(지도)를 기록했다.[3]
  • 대규모 약지도 사전 학습: E5는 웹에서 모은 대량의 텍스트 쌍(CCPairs)으로 대조 학습을 한 뒤 미세 조정했고, 레이블 데이터 없이 BEIR 검색 벤치마크에서 BM25를 처음 앞선 모델이라고 보고했다.[4] 이후 대부분의 범용 임베딩 모델이 "대규모 약지도 대조 학습 → 하드 네거티브를 넣은 지도 미세 조정" 2단계를 따른다.
  • 지시문·접두어: 같은 모델로 질의와 문서를 다르게 인코딩하도록 입력 앞에 표지를 붙인다. multilingual-e5는 모든 입력을 "query: " 또는 "passage: "로 시작하라고 안내하고,[5] Qwen3-Embedding은 과제별 지시문을 넣으면 대부분의 과제에서 1~5% 좋아진다고 밝혔다.[6] 접두어를 빠뜨리면 성능이 떨어지므로 모델 카드를 꼭 확인한다.
  • 마트료시카 표현 학습(MRL): 벡터의 앞쪽 일부 차원만 잘라 써도 쓸 만하도록 여러 길이에서 손실을 함께 거는 방법이다.[7] 저장 공간과 검색 속도를 위해 1024차원 벡터를 256차원으로 잘라 쓰는 식으로 활용한다.
  • STS: 사람이 0~5점으로 매긴 문장 쌍 유사도와 모델 코사인 유사도의 스피어먼 상관. 한국어는 영어 STS-B와 NLI 학습 데이터를 기계 번역하고 검증·평가 데이터는 사람이 번역한 KorSTS·KorNLI가 2020년 공개되었고,[8] 한국어 이해 벤치마크 KLUE에도 STS 과제가 있다.[9]
  • BEIR: 18개 공개 데이터셋으로 검색 모델의 제로샷 일반화를 잰다. 2021년 발표 당시 BM25가 강한 기준선이고, 밀집 검색 모델은 도메인이 바뀌면 자주 BM25보다 못했다.[10]
  • MTEB(Massive Text Embedding Benchmark): 분류, 군집화, 쌍 분류, 재순위화, 검색, STS, 요약, 비텍스트 마이닝(bitext mining) 등 8개 과제, 58개 데이터셋, 112개 언어로 33개 모델을 비교하며 2022년 발표되었다. 모든 과제에서 가장 좋은 단일 모델은 없다는 것이 주요 결론이었다.[11] 후속 MMTEB는 품질 관리한 500개 이상의 과제와 250개 이상의 언어로 넓혔다.[12]

리더보드 순위는 평균 점수이므로, 실제로는 자기 데이터(언어, 도메인, 문서 길이)로 검색 재현율을 직접 재 보고 고르는 것이 안전하다. 공개 벤치마크 데이터가 학습에 섞였을 가능성도 고려한다(벤치마크 오염).

아래는 모델 카드로 확인한 예이며 성능 순위가 아니다.

모델 차원 최대 입력 특징
jhgan/ko-sroberta-multitask 768 - KorNLI·KorSTS로 다중 과제 학습한 한국어 SBERT. 모델 카드 기준 KorSTS 평가 코사인 스피어먼 85.60[13]
BM-K/KoSimCSE-roberta-multitask - - 한국어 SimCSE. 저장소 표 기준 STS 평가 평균 85.77[14]
intfloat/multilingual-e5-large 1024 - 24층 다국어 E5, "query: "/"passage: " 접두어 필요[5]
BAAI/bge-m3 1024 8192 토큰 100개 이상 언어, 밀집·희소·다중 벡터 검색을 한 모델에서 지원[15]
nlpai-lab/KURE-v1 1024 8192 토큰 고려대 NLP&AI 연구실이 BGE-M3를 한국어 질의-문서-하드 네거티브 데이터로 미세 조정한 검색용 모델[16]
Qwen3-Embedding (0.6B/4B/8B) 1024/2560/4096 32K 토큰 마지막 토큰 풀링, MRL과 지시문 지원. 8B 모델이 2025년 6월 5일 기준 MTEB 다국어 리더보드 1위(70.58)라고 밝혔다[6]

OpenAI, 구글, Cohere 등은 API로만 쓰는 임베딩 모델을 제공한다. 같은 벡터 공간을 유지하려면 문서와 질의를 반드시 같은 모델(같은 버전)로 인코딩해야 하며, 모델을 바꾸면 색인 전체를 다시 만들어야 한다.

sentence-transformers 라이브러리(6.1.0 기준)로 인코딩과 유사도 계산을 하는 예다. API는 모델 카드 예제와 같다.

from sentence_transformers import SentenceTransformer

model = SentenceTransformer("jhgan/ko-sroberta-multitask")
sentences = [
    "치타가 들판을 가로질러 먹이를 쫓는다.",
    "치타 한 마리가 먹이 뒤에서 달리고 있다.",
    "원숭이 한 마리가 드럼을 연주한다.",
]
emb = model.encode(sentences, normalize_embeddings=True)   # (3, 768), L2 정규화
print(model.similarity(emb, emb))                            # 3x3 코사인 유사도 행렬

라이브러리 없이 허깅 페이스 Transformers로 평균 풀링을 직접 하면 다음과 같다. 패딩 토큰을 평균에서 빼는 것이 핵심이다.

import torch
import torch.nn.functional as F
from transformers import AutoTokenizer, AutoModel

name = "jhgan/ko-sroberta-multitask"
tok, enc = AutoTokenizer.from_pretrained(name), AutoModel.from_pretrained(name)

def embed(texts):
    batch = tok(texts, padding=True, truncation=True, return_tensors="pt")
    with torch.no_grad():
        h = enc(**batch).last_hidden_state                     # (B, L, H)
    mask = batch["attention_mask"].unsqueeze(-1).float()       # (B, L, 1)
    u = (h * mask).sum(1) / mask.sum(1).clamp(min=1e-9)       # 평균 풀링
    return F.normalize(u, dim=-1)

q, d = embed(["환불은 며칠 안에 되나요?"]), embed(["결제 취소 후 3~5영업일 안에 환불됩니다."])
print((q @ d.T).item())

자기 데이터로 미세 조정할 때는 (질의, 정답) 쌍을 모아 대조 학습 손실로 학습한다.

from datasets import Dataset
from sentence_transformers import SentenceTransformer, SentenceTransformerTrainer, losses

model = SentenceTransformer("jhgan/ko-sroberta-multitask")
train = Dataset.from_dict({
    "anchor":   ["비밀번호를 잊어버렸어요", "배송 조회는 어디서 하나요"],
    "positive": ["로그인 화면의 '비밀번호 찾기'를 누르세요", "마이페이지 > 주문 내역에서 배송 상태를 볼 수 있습니다"],
})
loss = losses.MultipleNegativesRankingLoss(model)   # 배치 내 음성 InfoNCE, scale=20(τ=0.05)
SentenceTransformerTrainer(model=model, train_dataset=train, loss=loss).train()

(anchor, positive, negative) 세 열을 주면 세 번째 열이 하드 네거티브로 분모에 추가된다. 배치 내 음성을 쓰므로 배치를 키울수록 유리하고, 같은 정답이 한 배치에 두 번 들어가지 않게 하는 것이 좋다.

한계와 주의점

편집 원본 편집
  • 정보 압축: 긴 문서를 벡터 하나로 줄이면 세부 내용이 사라진다. 그래서 문서를 청크로 잘라 넣고(RAG (인공지능) 참고), 정밀도가 필요하면 토큰별 벡터를 쓰는 ColBERT나 리랭커를 덧붙인다.
  • 정확 일치에 약함: 제품 번호, 오류 코드, 고유명사처럼 철자가 그대로 맞아야 하는 질의는 BM25 같은 어휘 검색이 낫다. 둘을 섞는 것이 하이브리드 검색이다.
  • 부정·수치: "환불이 된다"와 "환불이 안 된다"처럼 부정어 하나 차이, 숫자 차이는 벡터가 매우 가깝게 나오기 쉽다.
  • 도메인·언어: 일반 영어 데이터로 학습한 모델은 한국어, 법률·의료 문서에서 품질이 떨어질 수 있다. 다국어 모델이나 해당 언어로 미세 조정한 모델을 고르고 직접 평가한다.
  • 유사도 값의 의미: 코사인 값의 절대 크기는 모델마다 분포가 달라 "0.8 이상이면 같은 뜻" 같은 고정 임계값은 모델을 바꾸면 맞지 않는다.
  1. ↑ 1.0 1.1 1.2 1.3 Nils Reimers, Iryna Gurevych, 〈Sentence-BERT: Sentence Embeddings using Siamese BERT-Networks〉, EMNLP 2019. arXiv:1908.10084
  2. ↑ Kawin Ethayarajh, 〈How Contextual are Contextualized Word Representations?〉, EMNLP 2019. arXiv:1909.00512
  3. ↑ Tianyu Gao, Xingcheng Yao, Danqi Chen, 〈SimCSE: Simple Contrastive Learning of Sentence Embeddings〉, EMNLP 2021. arXiv:2104.08821
  4. ↑ Liang Wang 외, 〈Text Embeddings by Weakly-Supervised Contrastive Pre-training〉, 2022. arXiv:2212.03533
  5. ↑ 5.0 5.1 intfloat/multilingual-e5-large 모델 카드
  6. ↑ 6.0 6.1 Qwen3-Reranker-0.6B 모델 카드(Qwen3 Embedding 시리즈 소개 포함)
  7. ↑ Aditya Kusupati 외, 〈Matryoshka Representation Learning〉, NeurIPS 2022. arXiv:2205.13147
  8. ↑ Jiyeon Ham 외, 〈KorNLI and KorSTS: New Benchmark Datasets for Korean Natural Language Understanding〉, 2020. arXiv:2004.03289
  9. ↑ Sungjoon Park 외, 〈KLUE: Korean Language Understanding Evaluation〉, 2021. arXiv:2105.09680
  10. ↑ Nandan Thakur 외, 〈BEIR: A Heterogenous Benchmark for Zero-shot Evaluation of Information Retrieval Models〉, NeurIPS 2021 Datasets and Benchmarks. arXiv:2104.08663
  11. ↑ Niklas Muennighoff, Nouamane Tazi, Loïc Magne, Nils Reimers, 〈MTEB: Massive Text Embedding Benchmark〉, 2022. arXiv:2210.07316
  12. ↑ Kenneth Enevoldsen 외, 〈MMTEB: Massive Multilingual Text Embedding Benchmark〉, 2025. arXiv:2502.13595
  13. ↑ jhgan/ko-sroberta-multitask 모델 카드
  14. ↑ BM-K/KoSimCSE-roberta-multitask 모델 카드
  15. ↑ Jianlv Chen 외, 〈M3-Embedding: Multi-Linguality, Multi-Functionality, Multi-Granularity Text Embeddings Through Self-Knowledge Distillation〉, 2024. arXiv:2402.03216
  16. ↑ nlpai-lab/KURE-v1 모델 카드