Embedding 与向量数据库
RAG 的召回质量上限由 Embedding 决定,召回效率由向量数据库决定。这两块的原理与选型是 RAG 面试的必考区。
Embedding(嵌入)
Embedding 把文本映射成稠密向量,让「语义相近的文本,向量也相近」。RAG 的检索本质就是「在向量空间里找离 query 最近的文档」。
相似度度量
- 余弦相似度(Cosine):看方向夹角,与长度无关,最常用。
- 点积(Dot Product):同时受方向和模长影响,归一化后等价于余弦。
- 欧氏距离(L2):看绝对距离。
大多数文本 Embedding 模型输出已归一化的向量,此时余弦相似度 = 点积,且与 L2 距离单调相关,选哪个度量结果一致。
Embedding 模型选型
| 类型 | 代表 | 特点 |
|---|---|---|
| 闭源 API | OpenAI text-embedding-3 | 开箱即用、质量稳定,需联网、按量付费 |
| 开源中文 | BGE(智源)、M3E、GTE | 中文强、可私有化部署、免费 |
| 多语言/多功能 | BGE-M3 | 同时支持稠密、稀疏、多向量,一模多用 |
选型要点:任务领域、语言(中文优先 BGE/GTE 系列)、向量维度(影响存储与速度)、是否需私有化、最大输入长度。可参考 MTEB 榜单,但务必在自己的业务数据上实测。领域差异大时可微调 Embedding 模型。
Bi-Encoder vs Cross-Encoder
- Bi-Encoder(双塔):query 和文档分别编码成向量,可离线预计算文档向量、在线只算 query,快,适合海量召回(Embedding 模型属于此类)。
- Cross-Encoder(交叉编码):把 query 和文档拼在一起输入模型打分,精度高但无法预计算、慢,只能用于对少量候选重排(Rerank)。
这就是 RAG「向量召回(bi-encoder)粗筛 + Rerank(cross-encoder)精排」两段式的原理。
向量数据库
向量库负责高效存储海量向量,并快速找出与 query 最近的 Top-K。核心是 ANN(近似最近邻)索引。
为什么用 ANN 而不是精确检索?
精确检索(暴力遍历)在百万/亿级向量上太慢(O(N))。ANN(Approximate Nearest Neighbor) 用牺牲极小精度换取数量级的速度提升。
主流 ANN 索引
- HNSW(分层可导航小世界图):构建多层图,上层稀疏(快速跳转)、下层稠密(精细搜索),查询是「在图上贪心找最近邻」。查询快、召回高,内存占用大,是目前最主流的索引。
- IVF(倒排文件):先用聚类把向量分桶,查询时只搜最近的几个桶。省内存,需训练聚类中心。
- PQ(乘积量化):把向量切段后量化压缩,大幅省内存,常与 IVF 组合成 IVF-PQ,适合超大规模。
一句话:追求精度/速度选 HNSW,追求省内存/超大规模选 IVF-PQ。
向量数据库选型
| 数据库 | 特点 |
|---|---|
| Faiss | Meta 出品的向量检索库(非完整 DB),算法全、性能强,常作底层 |
| Milvus | 功能完整、可水平扩展,生产级首选 |
| Qdrant | Rust 编写,性能好、过滤能力强,轻量易用 |
| Chroma | 极简,适合本地开发和原型 |
| pgvector | PostgreSQL 插件,已有 PG 技术栈时无缝集成 |
| Pinecone / Zilliz | 全托管云服务,免运维 |
选型考虑:数据规模、是否需要元数据过滤、是否要分布式扩展、运维成本、与现有技术栈的契合度。中小规模或已有 PG → pgvector;大规模生产 → Milvus;快速验证 → Chroma。
高频追问
Q:向量维度越高越好吗? 不是。维度高语义表达更细,但存储、内存、检索成本都上升,还有「维度灾难」。需在效果和成本间权衡,很多场景 768/1024 维已够用,部分模型支持 MRL(套娃表示) 可按需截断维度。
Q:HNSW 为什么快又准? 它把向量组织成可导航的小世界图,搜索时从高层入口贪心地向更近的邻居跳转,逐层下沉精细化,平均复杂度接近 O(log N),且召回率高;代价是图结构占内存大、构建慢。
Q:稀疏向量和稠密向量的区别?什么时候用混合检索? 稠密向量(Embedding)擅长语义相似;稀疏向量(BM25/SPLADE)擅长精确匹配关键词、专有名词、术语、编号。当 query 含具体术语或编号时稠密检索常失灵,用混合检索(Hybrid)+ RRF 融合互补,详见 RAG 进阶。
Q:Embedding 要不要和生成模型用同一家? 不必。Embedding 和 LLM 可解耦,按各自最优选型即可。但 query 和文档必须用同一个 Embedding 模型编码,否则向量空间不一致、检索失效。
Q:文档更新了,向量库怎么同步? 增量更新——对变更文档重新切分、向量化并 upsert,删除失效向量。需要维护文档与向量的映射关系(如按文档 ID 管理),避免全量重建。