检索增强生成(RAG)入门:原理、架构与实践

1. 什么是 RAG?

检索增强生成(Retrieval-Augmented Generation,简称 RAG)是一种将信息检索(或向量搜索)与大型语言模型(LLM)生成能力相结合的技术架构。其核心思想是:在 LLM 生成答案之前,先从外部知识库(如文档、数据库、网页)中检索出与用户问题最相关的信息片段,然后将这些信息作为上下文提供给 LLM,从而生成更准确、更具事实依据且能减少"幻觉"的答案。

简单来说,RAG 让 LLM 具备了"实时查资料"的能力。

2. RAG 的核心价值

  • 减少幻觉(Hallucination):LLM 仅依赖其训练数据中的知识,可能生成看似合理但事实错误的内容。RAG 通过提供来自可信知识源的准确上下文,极大地降低了这种风险。
  • 知识实时更新:LLM 的训练成本高昂,知识存在滞后性。RAG 可以随时更新其背后的知识库(如添加最新产品文档、新闻),让模型能够回答关于新知识的问题,而无需重新训练模型。
  • 增强可控性与可解释性:系统可以记录为每次回答提供了哪些参考文档,增强了答案的可追溯性和可信度。开发者也能更好地控制模型的知识边界。
  • 保护私有数据:企业可以将内部文档、代码库、客户数据作为知识库,而无需将这些敏感数据用于训练 LLM,只需在推理时安全地检索即可。

3. RAG 的基本工作流程

一个典型的 RAG 系统通常包含以下步骤:

  1. 索引(Indexing):

    • 文档加载:从各种来源(PDF、Word、网页、数据库)加载文档。
    • 文本分割(Chunking):将长文档切分成更小的、语义连贯的片段(chunks)。这是关键步骤,分割质量直接影响检索效果。
    • 向量化(Embedding):使用嵌入模型(Embedding Model)将每个文本片段转换为高维向量(即向量表示)。
    • 存储:将这些向量及其对应的原始文本存储到向量数据库(如 Pinecone、Weaviate、Milvus、Chroma)中。
  2. 检索(Retrieval):

    • 当用户提出一个问题(Query)时,系统使用相同的嵌入模型将问题转换为查询向量。
    • 在向量数据库中执行相似性搜索(如余弦相似度),找出与查询向量最相似的 K 个文本片段(及其源文档)。
  3. 增强(Augmentation):

    • 将检索到的 top-K 个相关文本片段(作为上下文)与用户的原始问题组合,构造出一个增强的提示(Prompt)提交给 LLM。
  4. 生成(Generation):

    • LLM 基于提供的上下文和问题,生成最终的回答。

#mermaid-svg-VSeFWVlYn53ZjPUi{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}@keyframes edge-animation-frame{from{stroke-dashoffset:0;}}@keyframes dash{to{stroke-dashoffset:0;}}#mermaid-svg-VSeFWVlYn53ZjPUi .edge-animation-slow{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 50s linear infinite;stroke-linecap:round;}#mermaid-svg-VSeFWVlYn53ZjPUi .edge-animation-fast{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 20s linear infinite;stroke-linecap:round;}#mermaid-svg-VSeFWVlYn53ZjPUi .error-icon{fill:#552222;}#mermaid-svg-VSeFWVlYn53ZjPUi .error-text{fill:#552222;stroke:#552222;}#mermaid-svg-VSeFWVlYn53ZjPUi .edge-thickness-normal{stroke-width:1px;}#mermaid-svg-VSeFWVlYn53ZjPUi .edge-thickness-thick{stroke-width:3.5px;}#mermaid-svg-VSeFWVlYn53ZjPUi .edge-pattern-solid{stroke-dasharray:0;}#mermaid-svg-VSeFWVlYn53ZjPUi .edge-thickness-invisible{stroke-width:0;fill:none;}#mermaid-svg-VSeFWVlYn53ZjPUi .edge-pattern-dashed{stroke-dasharray:3;}#mermaid-svg-VSeFWVlYn53ZjPUi .edge-pattern-dotted{stroke-dasharray:2;}#mermaid-svg-VSeFWVlYn53ZjPUi .marker{fill:#333333;stroke:#333333;}#mermaid-svg-VSeFWVlYn53ZjPUi .marker.cross{stroke:#333333;}#mermaid-svg-VSeFWVlYn53ZjPUi svg{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;}#mermaid-svg-VSeFWVlYn53ZjPUi p{margin:0;}#mermaid-svg-VSeFWVlYn53ZjPUi .label{font-family:"trebuchet ms",verdana,arial,sans-serif;color:#333;}#mermaid-svg-VSeFWVlYn53ZjPUi .cluster-label text{fill:#333;}#mermaid-svg-VSeFWVlYn53ZjPUi .cluster-label span{color:#333;}#mermaid-svg-VSeFWVlYn53ZjPUi .cluster-label span p{background-color:transparent;}#mermaid-svg-VSeFWVlYn53ZjPUi .label text,#mermaid-svg-VSeFWVlYn53ZjPUi span{fill:#333;color:#333;}#mermaid-svg-VSeFWVlYn53ZjPUi .node rect,#mermaid-svg-VSeFWVlYn53ZjPUi .node circle,#mermaid-svg-VSeFWVlYn53ZjPUi .node ellipse,#mermaid-svg-VSeFWVlYn53ZjPUi .node polygon,#mermaid-svg-VSeFWVlYn53ZjPUi .node path{fill:#ECECFF;stroke:#9370DB;stroke-width:1px;}#mermaid-svg-VSeFWVlYn53ZjPUi .rough-node .label text,#mermaid-svg-VSeFWVlYn53ZjPUi .node .label text,#mermaid-svg-VSeFWVlYn53ZjPUi .image-shape .label,#mermaid-svg-VSeFWVlYn53ZjPUi .icon-shape .label{text-anchor:middle;}#mermaid-svg-VSeFWVlYn53ZjPUi .node .katex path{fill:#000;stroke:#000;stroke-width:1px;}#mermaid-svg-VSeFWVlYn53ZjPUi .rough-node .label,#mermaid-svg-VSeFWVlYn53ZjPUi .node .label,#mermaid-svg-VSeFWVlYn53ZjPUi .image-shape .label,#mermaid-svg-VSeFWVlYn53ZjPUi .icon-shape .label{text-align:center;}#mermaid-svg-VSeFWVlYn53ZjPUi .node.clickable{cursor:pointer;}#mermaid-svg-VSeFWVlYn53ZjPUi .root .anchor path{fill:#333333!important;stroke-width:0;stroke:#333333;}#mermaid-svg-VSeFWVlYn53ZjPUi .arrowheadPath{fill:#333333;}#mermaid-svg-VSeFWVlYn53ZjPUi .edgePath .path{stroke:#333333;stroke-width:2.0px;}#mermaid-svg-VSeFWVlYn53ZjPUi .flowchart-link{stroke:#333333;fill:none;}#mermaid-svg-VSeFWVlYn53ZjPUi .edgeLabel{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-VSeFWVlYn53ZjPUi .edgeLabel p{background-color:rgba(232,232,232, 0.8);}#mermaid-svg-VSeFWVlYn53ZjPUi .edgeLabel rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-VSeFWVlYn53ZjPUi .labelBkg{background-color:rgba(232, 232, 232, 0.5);}#mermaid-svg-VSeFWVlYn53ZjPUi .cluster rect{fill:#ffffde;stroke:#aaaa33;stroke-width:1px;}#mermaid-svg-VSeFWVlYn53ZjPUi .cluster text{fill:#333;}#mermaid-svg-VSeFWVlYn53ZjPUi .cluster span{color:#333;}#mermaid-svg-VSeFWVlYn53ZjPUi div.mermaidTooltip{position:absolute;text-align:center;max-width:200px;padding:2px;font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:12px;background:hsl(80, 100%, 96.2745098039%);border:1px solid #aaaa33;border-radius:2px;pointer-events:none;z-index:100;}#mermaid-svg-VSeFWVlYn53ZjPUi .flowchartTitleText{text-anchor:middle;font-size:18px;fill:#333;}#mermaid-svg-VSeFWVlYn53ZjPUi rect.text{fill:none;stroke-width:0;}#mermaid-svg-VSeFWVlYn53ZjPUi .icon-shape,#mermaid-svg-VSeFWVlYn53ZjPUi .image-shape{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-VSeFWVlYn53ZjPUi .icon-shape p,#mermaid-svg-VSeFWVlYn53ZjPUi .image-shape p{background-color:rgba(232,232,232, 0.8);padding:2px;}#mermaid-svg-VSeFWVlYn53ZjPUi .icon-shape .label rect,#mermaid-svg-VSeFWVlYn53ZjPUi .image-shape .label rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-VSeFWVlYn53ZjPUi .label-icon{display:inline-block;height:1em;overflow:visible;vertical-align:-0.125em;}#mermaid-svg-VSeFWVlYn53ZjPUi .node .label-icon path{fill:currentColor;stroke:revert;stroke-width:revert;}#mermaid-svg-VSeFWVlYn53ZjPUi :root{--mermaid-font-family:"trebuchet ms",verdana,arial,sans-serif;} "原始文档

(知识库)"
"文本分割

(Chunking)"
"向量化

(Embedding)"
"向量数据库

(Vector DB)"
"用户提问

(Query)"
"向量化

(Embedding)"
"相似性检索

(Similarity Search)"
"检索到的相关上下文

(Top-K Chunks)"
"构造增强提示

(Prompt)"
"大语言模型

(LLM)"
"最终答案

(Answer)"

4. 关键组件与技术选型

  • 文档加载器:LangChain Document Loaders、LlamaIndex、Unstructured。
  • 文本分割器:按字符、递归按分隔符、按标记(Token)或基于语义的分割。
  • 嵌入模型 :OpenAI text-embedding-3-*、Cohere Embed、BGE(智源)、all-MiniLM-L6-v2(开源轻量)。
  • 向量数据库:Pinecone(云服务)、Weaviate(开源)、Milvus(开源)、Chroma(轻量开源)、Qdrant。
  • 大语言模型(LLM):GPT-4、Claude、Gemini 或开源模型如 Llama、Qwen、DeepSeek。
  • 编排框架:LangChain、LlamaIndex 提供了构建 RAG 流水线的高级抽象。

5. 一个简单的代码示例(使用 LangChain)

以下是一个使用 LangChain 和 OpenAI 构建最小化 RAG 管道的示例:

python 复制代码
# 环境准备:pip install langchain-openai langchain-chroma
from langchain_openai import OpenAIEmbeddings, ChatOpenAI
from langchain_chroma import Chroma
from langchain_core.documents import Document
from langchain_core.prompts import ChatPromptTemplate
from langchain.chains.combine_documents import create_stuff_documents_chain

# 1. 模拟知识库文档
documents = [
    Document(page_content="LangChain 是一个用于开发由大语言模型驱动的应用程序的框架。"),
    Document(page_content="RAG 结合了检索和生成,以提高回答的准确性。"),
    Document(page_content="向量数据库用于高效存储和检索嵌入向量。"),
]

# 2. 创建嵌入模型和向量存储
embeddings = OpenAIEmbeddings(model="text-embedding-3-small")
vectorstore = Chroma.from_documents(documents, embeddings)

# 3. 创建检索器
retriever = vectorstore.as_retriever(search_kwargs={"k": 2})

# 4. 定义 LLM
llm = ChatOpenAI(model="gpt-4o-mini")

# 5. 定义提示模板
prompt = ChatPromptTemplate.from_template("""
请根据以下上下文回答问题。如果上下文不包含相关信息,请说"根据已知信息无法回答"。

上下文:
{context}

问题:{input}
""")

# 6. 创建链
document_chain = create_stuff_documents_chain(llm, prompt)

# 模拟用户查询
query = "LangChain 是什么?"
# 检索上下文
retrieved_docs = retriever.invoke(query)
# 生成答案
context = "\n\n".join([doc.page_content for doc in retrieved_docs])
answer = document_chain.invoke({"context": context, "input": query})

print(f"问题:{query}")
print(f"答案:{answer}")

6. 进阶优化方向

基础的 RAG 可能面临"检索精度不足"、"上下文窗口限制"等问题,常见的优化策略包括:

  • 查询转换:对原始查询进行重写、扩展或分解,以提升检索效果。
  • 混合搜索(Hybrid Search):结合关键词搜索(如 BM25)和向量搜索,兼顾精确匹配和语义相似度。
  • 重排序(Re-ranking):使用更精细的模型对初步检索结果进行重新排序,将最相关的片段排在前面。
  • 上下文压缩:对检索到的长文档进行摘要或过滤,只保留最相关的部分,以节省上下文窗口。
  • 多跳检索(Multi-hop Retrieval):对于复杂问题,进行多次检索-推理循环,逐步深入。

7. 总结

RAG 已成为构建基于私有知识、事实准确、可解释的 AI 应用的主流范式。它巧妙地弥补了 LLM 在事实性、时效性和数据隐私方面的短板。从简单的文档问答到复杂的智能客服、知识库助手,RAG 都扮演着核心角色。掌握其基本原理和实现,是开发现代 AI 应用的关键一步。

相关推荐
码上观世界4 小时前
Paseo 是如何统一管理 Claude Code 和 Codex 的?
人工智能·codex
长弓三石4 小时前
把 AgentScope Harness 装进 RuoYi-Vue-Plus:纯 Java AI 平台的集成实践
java·人工智能·agent
思考着亮4 小时前
3.什么是Harness Engineering?什么又是Loop Engineering?
人工智能
蜗牛互联网4 小时前
MongoDB Atlas Agent Engine之后,如何用版本门禁防止陈旧写入
java·数据库·人工智能·后端·mongodb
长弓三石4 小时前
企业级智能体的权限到底怎么落地?以 BizBuddy 为例
java·人工智能·agent
慢云智慧空间5 小时前
从智能终端到空间AI,慢云科技如何重新定义智慧建筑的核心能力?
人工智能·python·科技
合调于形5 小时前
Jusshen zhzzneng《具身智能》词条汉语拼音字母标调拼写实测案例
人工智能·自然语言处理·人机交互·语音识别·学习方法
DP DPharness5 小时前
cc-safety-net 上手指南:从 npx install 到 doctor 自检
人工智能·dpharness
youdexiang5 小时前
会议记录工具哪个好?搜索能力横评
人工智能
倔强的石头1065 小时前
【Linux指南】动静态库系列(十一):PLT 与延迟绑定:第一次调用动态库函数时发生了什么
linux·人工智能·python