Advanced RAG

张开发
2026/5/23 8:28:20 15 分钟阅读
Advanced RAG
一. RAG存在的问题1. RAG流程回顾RAG具体实现流程回顾加载文件 读取文本 文本分割 文本向量化 问句向量化 在文本向量中匹配出与问句向量最相似的 top k 个 匹配出的文本作为上下文和问题一起添加到 prompt 中 提交给 LLM 生成回答2. RAG痛点分析RAG痛点问题分析论文论文:《Seven Failure Points When Engineering a Retrieval Augmented Generation System》地址https://arxiv.org/pdf/2401.058562.1 具体痛点问题总结基本RAG流程可以分为两大块文本向量化构建索引的过程Index Process和检索增强问答的过程Query Process。failure point:故障点 Data flow:数据流processing stage: 处理阶段 Text input/output: 文本输入/输出Index Process文本向量化构建索引的过程:加载过程:输入原始文档 -- 文档分割 -- 向量处理存入数据库MIssing Content(内容缺失):原本的文本中就没有问题的答案文档加载准确性和效率比如pdf文件的加载如何提取其中的有用文字信息和图片信息等文档切分的粒度文本切分的大小和位置会影响后面检索出来的上下文完整性和与大模型交互的token数量怎么控制好文档切分的度是个难题。Query Process检索增强回答的过程中:查询过程: 用户提交问题 -- 查询重写器对问题进行重新表述 -- 检索器去数据库检索相关内容 -- 对检索的块进行重排生成列表 -- 合并整理列表中的块 -- 读取合并之后的块 -- 生成响应返回给用户Missed Top Ranked:错过排名靠前的文档Not in Context:提取上下文与答案无关Wrong Format(格式错误):例如需要Json给了字符串Incomplete(答案不完整):答案只回答了问题的一部分Not Extracted(未提取到答案:)提取的上下文中有答案但大模型没有提取出来Incorrect Specificity:答案不够具体或过于具体二. RAG优化1. 内容缺失准备的外挂文本中没有回答问题所需的知识。这时候RAG可能会提供一个自己编造的答案。增加相应知识库将相应的知识文本加入到向量知识库中。数据清洗与增强输入垃圾那也必定输出垃圾。如果你的源数据质量低劣比如包含互相冲突的信息那不管你的 RAG 工作构建得多么好它都不可能用你输入的垃圾神奇地输出高质量结果。这个解决方案不仅适用于这个痛点任何RAG工作流程想要获得优良表现都必须先清洁数据。更好的Prompt设计通过Prompts让大模型在找不到答案的情况下输出“根据当前知识库无法回答该问题”(不让他胡乱回答)等提示。这样的提示就能鼓励模型承认自己的局限并更透明地向用户传达它的不确定。虽然不能保证 100% 准确度但在清洁数据之后精心设计 prompt 是最好的做法之一。2. 文档加载准确性和效率优化文档读取器一般知识库中的文档格式都不尽相同HTML、PDF、MarkDown、TXT、CSV等。每种格式文档都有其都有的数据组织方式。怎么在读取这些数据时将干扰项去除如一些特殊符号等同时还保留原文本之间的关联关系如csv文件保留其原有的表格结构是主要的优化方向。 目前针对这方面的探索为针对每一类文档涉及一个专门的读取器。如LangChain中提供的WebBaseLoader专门用来加载HTML文本等。 网址:https://python.langchain.com/v0.1/docs/modules/data_connection/document_loaders/数据清洗与增强输入垃圾那也必定输出垃圾。如果你的源数据质量低劣比如包含互相冲突的信息那不管你的 RAG 工作构建得多么好它都不可能用你输入的垃圾神奇地输出高质量结果。这个解决方案不仅适用于这个痛点任何RAG工作流程想要获得优良表现都必须先清洁数据。3. 文档切分的粒度粒度太大可能导致检索到的文本包含太多不相关的信息降低检索准确性粒度太小可能导致信息不全面导致答案的片面性。问题的答案可能跨越两个甚至多个片段固定长度的分块直接设定块中的字数每个文本块有多少字。内容重叠分块在固定大小分块的基础上为了保持文本块之间语义上下文的连贯性在分块时保持文本块之间有一定的内容重叠。基于结构的分块基于结构的分块方法利用文档的固有结构如HTML或Markdown中的标题和段落以保持内容的逻辑性和完整性。基 分块重复的利用分块规则不断细分文本块。在langchain中会先通过段落换行符\n\n进行分割。然后检查这些块的大小。如果大小不超过一定阈值则该块被保留。对于大小超过标准的块使用单换行符\n再次分割。以此类推不断根据块大小更新更小的分块规则如空格句号。分块大小的选择不同的嵌入模型有其最佳输入大小。比如Openai的text-embedding-ada-002的模型在256 或 512大小的块上效果更好。文档的类型和用户查询的长度及复杂性也是决定分块大小的重要因素。处理长篇文章或书籍时较大的分块有助于保留更多的上下文和主题连贯性而对于社交媒体帖子较小的分块可能更适合捕捉每个帖子的精确语义。如果用户的查询通常是简短和具体的较小的分块可能更为合适相反如果查询较为复杂可能需要更大的分块。4. 错过排名靠前的文档外挂知识库中存在回 答问题所需的知识但是可能这个知识块与问题的向量相似度排名并不是靠前的导致无法召回该知识块传给大模型导致大模型始终无法得到正确的答案。增加召回数量增加召回的 topK 数量也就是说例如原来召回前3个知识块修改为召回前5个知识块。不推荐此种方法因为知识块多了不光会增加token消耗也会增加大模型回答问题的干扰。重排Reranking该方法的步骤是首先检索出 topN 个知识块N K过召回然后再对这 topN 个知识块进行重排序取重排序后的 K 个知识块当作上下文。重排是利用另一个排序模型或排序策略对知识块和问题之间进行关系计算与排序。5. 提取上下文与答案无关内容缺失或错过排名靠前的文档的具体体现6. 格式错误Prompt调优优化Prompt逐渐让大模型返回正确的格式。Pydantic方法使用Pydantic进行结果格式验证例如使用LangChain中的PydanticOutputParser类来校验输出格式。通过 Pydantic你可以轻松地创建数据模型这些模型不仅能够验证输入的数据是否符合预期格式还能自动转换数据类型如将字符串转换为日期时间对象。Pydantic 特别适合处理 JSON 数据、环境变量配置等场景。参考:https://python.langchain.com/v0.2/docs/how_to/extraction_parse/#using-pydanticoutputparser7. 答案不完整将问题分开提问一方面引导用户精简问题一次只提问一个问题。 另一方面针对用户的问题进行内部拆分处理拆分成数个子问题等子问题答案都找到后再总结起来回复给用户8. 未提取到答案提示压缩技术在处理大型语言模型LLMs时提示压缩技术变得尤为重要尤其是当你面对输入长度限制或希望提高效率和减少成本的时候。提示压缩旨在减少提示的大小同时尽可能保持其表达的信息量和意图不变。网址:https://python.langchain.com/v0.2/docs/how_to/contextual_compression/#adding-contextual-compression-with-an-llmchainextractor9. 答案太具体或太笼统幻觉问题 暂无好的方案解决三. Advanced RAG前沿Paper解读1. 检索过程基于朴素RAG高级RAG主要通过预检索策略和后检索策略来提升检索质量。(可以更好的解决RAG的痛点)1.1 预检索过程高级RAG着重优化了索引结构和查询的方式。优化索引旨在提高被索引内容的质量包括增强数据颗粒度、优化索引结构、添加元数据、对齐优化和混合检索等策略。查询优化的目标则是明确用户的原始问题使其更适合检索任务使用了查询重写、查询转换、查询扩展等技术。查询重写Query Rewriting 目标在不改变查询意图的情况下重新表述查询使其更清晰、更适用于检索系统。 常用技术使用大语言模型LLM进行重写将原始查询输入LLM要求其生成一个或多个保留原意的改进版本。示例提示词请将以下用户查询改写成更清晰、更完整的句子同时保持原意不变。用户查询{query}查询转换Query Transformation 目标通过结构化的转换操作改变查询形式使其更适合检索。 常用技术关键词提取从查询中提取关键名词和动词忽略停用词和修饰词。分步查询Step-back Prompting将复杂查询分解为多个子问题然后分别检索最后再组合答案这通常需要多步检索。子问题分解将复杂问题分解成若干个简单的子问题每个子问题单独检索然后将所有检索结果合并提供给生成模型。查询扩展Query Expansion 目标在原始查询的基础上增加相关的术语或上下文以提供更丰富的检索信息。 常用技术使用LLM进行扩展直接让LLM生成与原始查询相关的扩展词或短语。多查询扩展Multi-Query Generation使用LLM生成多个与原始查询相关的不同表述的查询然后分别检索最后合并检索结果。1.2后检索过程对于由问题检索得到的一系列上下文后检索策略关注如何优化它们与查询问题的集成。这一过程主要包括重新排序和压缩上下文。重新排列检索到的信息将最相关的内容予以定位标记这种策略已经在LlamaIndex2、LangChain等框架中得以实施。直接将所有相关文档输入到大型语言模型LLMs可能导致信息过载为了缓解这一点后检索工作集中选择必要的信息强调关键部分并限制了了相应的上下文长度。2. Advanced RAG变体它们在基础 RAG 的框架上通过不同的技术路径和侧重点解决了特定场景下的问题方法核心优化方向关键技术亮点T-RAG任务/时间敏感检索分阶段检索、时效性优先CRAG检索质量动态修正置信度评估 重检索/人工干预Self-RAG生成过程自我反思LLM自我评估输出质量并触发检索GraphRAG知识图谱增强检索基于图结构的上下文推理RAG-Fusion多查询扩展检索生成多个相关查询合并结果Rewrite-Retrieve-Read查询重写优化先重写问题再检索提升检索适配性2.1 T-RAG论文地址https://arxiv.org/pdf/2402.07483目标开发一个可以安全、高效地回答私有企业文档问题的大型语言模型LLM应用程序主要考虑数据安全性、有限的计算资源以及需要健壮的应用程序来正确响应查询。方法应用程序结合了检索增强生成RAG和微调的开源 LLM将其称之为 Tree-RAGT-RAG。T-RAG 使用树结构来表示组织内的实体层次结构用于生成文本描述以增强对组织层次结构内的实体进行查询时的上下文。思路分析:用户提出一个查询。系统进行搜索和检索从向量数据库中查找相关的文档块作为上下文使用。如果查询涉及到组织中的实体从实体树中提取相关信息并添加到上下文中。示例问题“比较OpenAI的GPT-4和Google的PaLM 2的技术差异”实体树结构Root: 模型对比 ├─ OpenAI │ └─ GPT-4 │ ├─ 训练数据量 │ └─ 多模态能力 ├─ Google │ └─ PaLM 2 │ ├─ 能耗效率 │ └─ 多语言支持 └─ 对比维度 ├─ 参数量 └─ 应用场景 # 1. 任务拆解将复杂问题分解为实体关联的子任务 # 2. 精准检索针对每个实体分支生成特定检索查询减少噪声。 ​系统通过精调的LLM如Llama-2 7B模型生成响应。为了实现精调使用组织或领域特定的数据集对基础LLM进行微调。最后生成的响应返回给用户。2.2 CRAG可矫正的检索增强生成论文地址https://arxiv.org/pdf/2401.15884思路分析:Retrieval 阶段retriever 先根据 user query 检索到相关的 docsKnowledge Correction 阶段这里引入了一个轻量级的 Retrieval Evaluator 来评估检索到的 docs 与 user query 之间的相关性分数并根据这个相关性分数触发三种 action —— Correct、Incorrect 和 AmbiguousCorrect表示检索到的 doc 是有一定相关性的但尽管一个 doc 被认为是相关的该 doc 其中仍会存在噪音信息因此需要进一步地 refine所以这里将 docs 做 de-compose 得到多个 knowledge strips然后从中过滤出有用的 strip 并 re-compose得到矫正后的 doc。Incorrect表示可以认为所检索到的 docs 对 query 没有帮助因此需要寻找新的知识源这里引入 web searcher 来从 Internet 上进行检索并从中选出有用的知识得到矫正后的 doc。Ambiguous表示 retrieval evaluator 也没有信心说 docs 是否与 query 有关了这个时候会同时做 Correct 和 Incorrect 时的动作从而提高系统的鲁棒性(异常之后的处理)和可靠性。Generation 阶段将矫正后的 doc 与 user query 进行拼接交给 LLM Generator 来完成问题的回答。2.3 self-RAG可自我反思的检索增强生成论文地址https://arxiv.org/pdf/2310.11511参考 https://selfrag.github.io/思路分析:Retrieve on demand按需检索首先生成一个初步回答比如“美国各州的名字来源多种多样。”并根据回答中的需要检索文档。Generate segment in parallel并行生成段落并行生成Parallel Generation使用初步响应加上按需检索到的文档系统并行生成多个响应段落每个段落基于不同的文档和提示。评估生成段落Evaluate Segments系统对每个生成的段落进行评估判断其相关性和支持度。Critique outputs and select best segment评估输出并选择最佳段落评估输出Critique Outputs系统对生成的段落进行批判性评估选择最优的段落作为最终响应的一部分。重复检索和生成Repeat if necessary如果评估发现生成的段落仍不够准确系统可以重复检索和生成过程不断优化最终的响应。生成最终响应Generate Final Response最终的响应由多个最佳段落组合而成确保响应的准确性和完整性。2.4 RAG-Fusion项目地址https://github.com/Raudaschl/rag-fusion参考https://mp.weixin.qq.com/s/hxukMEeMzTEOVqd1P1fQLQ思路分析:通过LLM将用户的查询翻译成相似但不同的查询。对原始查询及其生成的类似查询进行向量搜索实现多个查询生成。使用RRF结合和精炼所有查询结果。选择新查询的所有顶部结果为LLM提供足够的材料以考虑所有查询和重排的结果列表来创建输出响应。2.5 Rewrite-Retrieve-Read RAG论文地址https://arxiv.org/pdf/2305.14283思路分析:Retrieve-then-read 方法输入Input用户提出查询。检索器Retriever系统从数据库中检索相关文档。文档读取器Black-box LLM Reader使用大型语言模型LLM读取检索到的文档并生成响应。输出Output提供给用户的最终响应。Rewrite-retrieve-read 方法输入Input用户提出查询。重写器LLM Rewriter使用LLM对原始查询进行重写以优化检索效果。检索器Web Search Retriever系统基于重写后的查询从数据库中检索相关文档。文档读取器Black-box LLM Reader使用LLM读取检索到的文档并生成响应。输出Output提供给用户的最终响应。Trainable rewrite-retrieve-read 方法输入Input用户提出查询。小型可训练重写器Small PrLM Rewriter使用一个小型、可训练的预训练语言模型PrLM对原始查询进行重写。检索器Web Search Retriever系统基于重写后的查询从数据库中检索相关文档。文档读取器Black-box LLM Reader使用LLM读取检索到的文档并生成响应。奖励机制Reward基于生成响应的质量对重写器进行反馈和训练以不断优化查询重写过程。输出Output提供给用户的最终响应。3.RAG与微调特点比对RAG是“外挂知识库”动态灵活但依赖检索质量。微调是“重塑模型”精准可控但需静态数据支撑。最佳实践根据任务特性实时性、领域深度、数据条件选择或组合两者。

更多文章