RAG可以更强
在使用大模型解决自定义场景问题的时候,往往由于大模型场景知识不足,而表现效果不佳,这种情况下,考虑如何让大模型学习当前场景的知识是必须要考虑解决的问题,通常情况下有两种方法:
- 微调:不论是全参数微调还是lora微调,都是将领域知识注入大模型的一种方法
- RAG:检索增强,通过检索召回方式,增强模型的输入上下文,使其了解领域知识
这两种方法各有利弊,微调是让大模型学会并记住了当前场景的知识,针对当前场景问题能够更加自如应对,当然,微调后的模型在通用性上效果会略有下降。后者是借助大模型的理解能力,在每次推理的输入中增加领域知识,大模型在当前交互过程中理解场景知识,但并不会记忆该知识,重新发起交互后,大模型对该场景还是一无所知的。
微调可以学会场景知识永久记忆,但微调过程对数据、算力依赖比较大,且场景知识更新后模型无法即时更新;RAG方式能够适配实时更新的知识,对数据和算力依赖较低,但非常依赖大模型自身的推理能力。
考虑到场景知识一般是动态变化的,RAG方法在实际中应用更加广泛,当然,如果场景条件允许,微调+RAG的方式或许是最优解。
典型的RAG流程
- 用户提出问题或提供指示。
- 系统查询矢量数据库以查找与用户的问题或指令相关的信息(“检索”)。
- 用户的提示和来自矢量数据库的任何相关信息都被提供给语言模型(“增强”)。
- 语言模型使用数据库中的信息来回答用户的提示(“生成”)。
在这个过程中,我们可以看到,场景知识通过检索的方式,与用户输入结合后,当做大模型的输入,增加大模型的生成能力。一般的检索过程是通过直接向量召回的方式,例如FAISS、Qdrant等向量库提供的向量相似,选择TOPK进行召回,和常规搜索、推荐的召回过程是类似的,也存在规则召回、向量召回或者文本召回等多种方式,但一般默认的是向量召回一种。
一般召回的TOPK内容直接和用户输入组合后,直接输入大模型,但这样的操作,是可以进一步优化的
- 召回的内容顺序可能影响大模型的生成效果,因为大模型是有输入长度限制的,如果相关内容在检索的最后,可能被截断,或者由于大模型对后续内容的权重降低导致回答不准确
- 召回的内容不一定都是相关的,由于向量化、相似度等方法的差异,召回的内容也存在一定相似准确率,召回
那如何解决这个问题呢?可以考虑进行重新排序和上下文压缩。
什么是重新排序?
可以参考搜索、推荐场景下,召回-排序的两阶段模式,可以吧检索看做是召回:根据相似性选择可能的候选文档集合,重新排序是对候选集合依据某些指标或方法,进行重新组织。
为什么需要重新排序?
- 一般来说,召回的内容越丰富,大模型生成质量越好,因为提供的信息足够的多,但召回内容的增多,可能导致相关信息位置靠后,导致大模型性能下降(context stuffing)
- 重新排序可以将最相关的放在前面,减少不相关信息对大模型的干扰
对内容进行重排后,基本能够保证最相关的在前面,但考虑召回机制是一种保召回的策略,召回内容中可能存在不相关甚至相反的噪声数据,例如“巴以冲突”进行召回,可能召回支持巴勒斯坦的新闻,也包含反对巴拉斯坦的新闻,在进行问答时候,可能导致模型无从下手。
什么是上下文压缩?
检索的一项挑战是,我们通常不知道我们的文档存储系统将面临哪些特定查询。这意味着与查询最相关的信息可能被隐藏在包含大量不相关文本的文档中。将整篇文章或全文输入到大模型中,可能会导致更差的结果和更高的相应时间。
上下文压缩旨在解决这个问题。
这个想法很简单,可以使用给定查询的上下文对其进行压缩,以便仅返回相关信息,而不是立即按原样返回检索到的文档。
instead of immediately returning retrieved documents as-is, you can compress them using the context of the given query, so that only the relevant information is returned.
这里的“压缩”既指压缩单个文档的内容,也指批量过滤文档。
要使用上下文压缩检索器,您需要:
- 检索器
- 文档压缩器
基于重排和压缩构建知识问答
一般的步骤如下:
- 检索器检索相关文档
- 相关文档进行压缩
- 压缩后的内容进行重排
下面我们基于langchain和CohereRerank实现上述流程
首先引入相关的包:
我们以一篇文本生成的英文论文为例,进行测试进行文档的加载和分割:
加载向量化模型,并使用FAISS作为检索器
从本地加载模型,构建推理需要的LLM
对比直接进行检索和检索重排后的效果与耗时情况
总结
微调是让大模型学会知识后,应用过程相当于闭卷考试,全靠自己学习记住的东西;RAG是大模型直接开卷考试,将所有知识摆在面前,能不能理解就看大模型自身的能力了。所以如何将检索的东西更加简单明了的输入到大模型中,是RAG方法的重点。