为什么需要 RAG?

大语言模型(LLM)虽然强大,但有两个硬伤:
- 知识截止日期:训练完成后就不再更新,不知道最新发生的事情
- 幻觉问题:不懂的问题也会编造答案,看起来有模有样但其实在胡说

RAG(Retrieval-Augmented Generation,检索增强生成)就是解决这两个问题的标准方案。

RAG 的核心流程

一句话概括:让模型在回答问题前,先去知识库里查一下相关资料,再根据查到的资料来回答。

整个流程分三步:

1. 索引(Indexing)—— 把知识库准备好

把文档(PDF、Wiki、数据库记录等)拆成小块(Chunk),每一块用 Embedding 模型转成向量(一串数字),存入向量数据库。

"什么是RAG?" → 向量化 → [0.023, -0.154, 0.672, ...] → 存入 Milvus/Qdrant

2. 检索(Retrieval)—— 找到相关内容

用户提问时,把问题也转成向量,去向量数据库里找最相似的 Top-K 个片段。

用户问:"RAG怎么减少幻觉?"
→ 向量化:用户问题
→ 向量检索:找到知识库里最相关的3个片段

3. 生成(Generation)—— 基于资料回答

把检索到的片段和用户问题一起拼成 Prompt,交给 LLM 生成最终答案。

System: 请基于以下资料回答问题:
[资料1] RAG通过引入外部知识减少幻觉...
[资料2] 知识库的质量直接影响RAG效果...

User: RAG怎么减少幻觉?

关键细节

Chunk 策略

切块是 RAG 效果的基础。常见的切法:
- 固定长度:256/512 tokens 一段,简单但可能切断语义
- 语义切分:按段落、句子边界切,效果更好
- 递归切分:先按段落切,太大的再按句子切,LangChain 的 RecursiveCharacterTextSplitter 就是这种

经验值:中文场景下,512 tokens 左右 + 128 tokens 重叠(Overlap)是比较稳妥的配置。

Embedding 选型

模型 维度 适用场景 推荐
text-embedding-3-small 1536 通用英文 OpenAI
bge-large-zh-v1.5 1024 中文场景 BAAI
stella-base-zh-v3 768 中文轻量 infgrad
m3e-base 768 中文通用 国产

中文场景优先选中文 Embedding 模型,英文模型的 tokenizer 对中文不友好,检索效果会明显差一截。

混合检索(Hybrid Search)

向量检索擅长语义匹配("苹果"→"iPhone"),但可能忽略精确关键词("iOS 18.3")。实际生产中推荐混合检索:
- 向量检索(语义相似度)× 关键词检索(BM25/全文匹配)
- 结果用 RRF(Reciprocal Rank Fusion)合并排序

# 混合检索伪代码
vec_results = vector_search(query, k=20)
kw_results = bm25_search(query, k=20)
merged = rrf_merge(vec_results, kw_results, k=5)

Re-ranking

检索到的 Top-K 结果用 Cross-Encoder 重排序,可以大幅提升最终效果。推荐:
- BAAI/bge-reranker-v2-m3(中文)
- cohere/rerank-multilingual-v3(收费)

进阶方向

  • Agentic RAG:让 Agent 决定什么时候去查知识库、查什么、查多少次
  • Graph RAG:用知识图谱代替向量库,适合需要多跳推理的场景(微软开源的 GraphRAG)
  • Multi-modal RAG:同时检索文本+图片,适合文档问答
  • Query 改写:把用户问题改写后再检索,效果往往比直接搜好

常用工具

  • LangChain / LlamaIndex:RAG 编排框架
  • Milvus / Qdrant / Chroma:向量数据库
  • Unstructured.io:文档解析
  • Jina AI:中文 RAG 工具链

总结

RAG 并不神秘,本质就是"先查资料再回答"。做好 RAG 的核心在于三个环节:
1. 切好块(Chunking)
2. 找得准(Retrieval)
3. 回答好(Generation)

每个环节都有很多优化空间,但从最简单的实现开始,跑通流程,再逐步优化,是最高效的学习路径。