導入
TF-IDFは「同じ単語が使われているか」という単語の一致に基づいた手法でした。手軽で仕組みも分かりやすい反面、“car” と “automobile” のような言い換えを同じ意味だと認識できません。実務のRAGでは、意味そのものを捉える本物の埋め込み(embedding)モデルを使います。ただしAPIキーの発行や、大きなモデルのダウンロードが必要で、この学習環境のブラウザ内では動かせないため、ここではコードを読みながら仕組みを押さえる回にします。
説明
「文字列を渡すと、数百〜数千次元の数値ベクトルが返ってくる」という点は、どの埋め込みAPIでも共通です。代表的な選択肢を3つ見てみましょう。APIキーはコードに直接書かず、環境変数から読み込むのが基本です。
(a) OpenAI の埋め込みモデル(text-embedding-3-small など)
import os
from openai import OpenAI
client = OpenAI(api_key=os.environ["OPENAI_API_KEY"])
response = client.embeddings.create(
model="text-embedding-3-small",
input="Retrieval-augmented generation combines search and generation.",
)
vector = response.data[0].embedding
print(len(vector)) # 1536次元のベクトル
(b) Voyage AI の埋め込みモデル(Anthropicが埋め込み用に推奨しているパートナー。voyage-3 など)
Anthropic自身はLLM(Claude)を提供していますが、テキストを検索用ベクトルに変換する「埋め込みモデル」は提供していません。その代わりに公式ドキュメントで案内されているのが Voyage AI です。
import os
import voyageai
vo = voyageai.Client(api_key=os.environ["VOYAGE_API_KEY"])
result = vo.embed(
["Retrieval-augmented generation combines search and generation."],
model="voyage-3",
input_type="document",
)
vector = result.embeddings[0]
print(len(vector)) # 1024次元のベクトル
(c) ローカルで動かす sentence-transformers(APIキー不要、自分のPCやサーバーで実行)
from sentence_transformers import SentenceTransformer
model = SentenceTransformer("all-MiniLM-L6-v2")
vector = model.encode("Retrieval-augmented generation combines search and generation.")
print(vector.shape) # (384,) の数値ベクトル
sentence-transformers はAPI呼び出しではなく、モデルそのものを手元にダウンロードして動かすライブラリです。API料金がかからずネットワーク越しの通信も不要ですが、モデルの実行に相応の計算資源(GPUがあれば高速)が必要になります。
3つとも呼び出し方は違いますが、やっていることは同じ――「文字列 → 数百〜数千次元のベクトル」への変換です。レッスン11の MiniVectorStore の TfidfVectorizer の部分を、これらの埋め込み関数に差し替えれば、単語の一致ではなく意味の近さで探すRAGになります。
まとめ
- TF-IDFは単語の一致に基づく手法。言い換えには弱いが、手軽でブラウザ内でも動く。
- 本物の埋め込みモデルは意味を捉えるが、APIキーやモデルのダウンロードが必要。
- OpenAI・Voyage AI(Anthropicが推奨)・
sentence-transformers(ローカル実行)はどれも「文字列 → ベクトル」という同じ役割を果たす。 MiniVectorStoreのベクトル化部分を差し替えるだけで、TF-IDF検索から意味検索へアップグレードできる。