RAG原理概述
RAG(Retrieval-Augmented Generation) 是一种结合了信息检索和生成式人工智能技术的模型架构,旨在让模型生成更有根据和更准确的回答。通俗来讲,它让模型不只是凭借自己的“记忆”(预训练数据)生成答案,还能即时去“查资料”,再结合查到的信息生成答案。它解决了模型只依赖自己有限的知识,回答不准确或过时的问题。
RAG的工作原理可以分为两部分:
-
检索(Retrieval):
- 当你向模型提出一个问题时,RAG 先会去一个外部知识库(比如一堆文档、维基百科、数据库等)“查找”相关内容。这就像你向搜索引擎询问某个问题,它会先给你返回一系列相关的网页或文章。
- 为了查找效率高,它把这些文档事先处理成计算机能够理解的“向量”(数字表示),方便进行快速匹配。
-
生成(Generation):
- 模型在查到的信息基础上进行“生成”,即使用一个类似于 GPT 这样的生成模型,结合检索到的内容,生成一个有逻辑、准确的回答。
- 比如你问一个问题,它查到相关的几段信息后,模型会把这些信息和自己的知识结合,生成一个自然语言的答案。
为什么 RAG 这么特别?
RAG 的关键好处是增强了生成模型的准确性。单纯的生成模型有时会“瞎猜”,尤其在面对最新的知识或较为专业的问题时。而 RAG 可以实时“查资料”,大大提高回答的准确性和时效性。
简单类比
- 单纯的生成模型:像一个很聪明的学生,知识广泛,但记忆有限,没办法查书,可能会给出一些不太准确的回答。
- RAG 模型:像一个知道自己不知道一切的学生,碰到不会的问题,可以去图书馆查资料再回答,答案自然更可靠。
应用场景
- 客服系统:能够根据公司文档或常见问题库生成精准的回答。
- 搜索引擎升级:提供比传统搜索引擎更智能的回答,既有检索又有生成。
- 医疗、法律等专业领域:实时查阅最新的相关文档,生成符合当前标准的建议。
总的来说,RAG 是一种让模型不仅“会想”,还“会查”的技术,能提升模型回答问题的准确性和实时性。
实战项目简介
我搭建的是一个Prompt技术的AI学习助手(基于自己搭建的和Prompt技术有关的文章与书籍)。
学习写Prompt需要一边写一边实践,否则就会“脑子说我会了,手说我废了”。平时看到好的Prompt,也会把它积累下来,也许哪天就能用上;在实践的时候,随着不断地修改,Prompt也会更新迭代;网上有很多学习Prompt技术好的资料(比如吴恩达出的Prompt Cookbook, 这个项目知识库里就有这本书),但是没有那么多时间去一一啃过,而且这类重实践的技术肯定是随学随用最好了,一边提问,大模型可以基于它本身的生成能力,以及知识库文档的内容,回答我的问题,同时根据我的需求帮我生成好的Prompt。
目前仅做了针对GPT、GLM生成文本类的Prompt,还没有加入Midjourney、stable diffusion的Prompt.
Embedding 模型:智谱清言配套的Embeding 模型
向量型数据库:Chroma
LLM : 调用ChatGLM-4的API
工具链:Langchain
前端:streamlit
知识库数据:
《面向开发者的LLM教程第一章:Engineering for Developers》(md文件)
《Prompt cookbook》(PDF文件)
安装依赖:
项目实战
一、知识库搭建
一般知识库的数据构建、清洗处理、转换成向量、存储到向量数据库都是提前离线做好的。经过一段时间再更新知识库内容时,还要把上面这些步骤再做一遍,一个上线的项目,这个过程可能是半个月或者一个月进行一次。
知识库的搭建包括以下几个部分:
-
数据预处理:收集相关的文本数据。数据源可以是结构化的数据库、非结构化的文本(如网页、PDF、Word 文档)、API 返回的内容、维基百科条目、社交媒体内容等。原始数据通常不适合直接使用,因此需要对数据进行清洗和预处理,如去掉无关的内容(广告、噪音)、标准化格式(统一编码、去除重复等)
-
数据分割:对于非结构化的长文档,需要将其分割成更小的片段(例如段落、句子)。片段的大小要合理,既保证能被检索到,又能让生成模型获取足够的信息来生成相关的回答。通常通过分段规则,如按段落或固定长度的字符数进行分割。
-
文本嵌入(向量化):预训练模型选择:选择适合的预训练模型来生成文本嵌入。常用的模型有 BERT、Sentence-BERT、OpenAI 的文本嵌入模型等。模型的选择会影响到后续的检索效果。
嵌入计算:将每一个片段转化为向量表示。这一步是将自然语言转化为固定维度的向量,以便后续通过向量相似度进行检索。
向量归一化:对生成的向量进行归一化处理,确保向量在检索时能够正确计算相似度(如使用余弦相似度或欧几里得距离)。 -
构建索引+向量入库:将所有文本片段的向量保存到向量数据库中,以便进行快速检索。常用的向量数据库有 Pinecone、FAISS、Milvus 等。这些数据库支持高效的相似度搜索,能够快速返回最相关的文档。
传统索引(可选):有时会将文本进行关键词索引(倒排索引),使用搜索引擎如 Elasticsearch、Whoosh 等。关键词搜索和向量搜索可以结合使用,以提高检索的准确性。
在搭建RAG应用的时候,一般都是用嵌入模型来构建词向量,此时有两个选择,一是选择在线大模型配套的Embedding模型 API,很多公司都有提供接口,不过有些是要付费的;再者也可以选择使用本地的Embedding模型,比如FlagEmbedding、BGE等等,目前已经有很多对中文语料进行Embedding表现得不错的开源模型,hugging face上有很多开源的中文Embedding模型可供选择。
本项目中我使用的是智谱清言的Embedding模型 API
主流的向量数据库有:Chroma、Weaviate、Qdrant等等,这里我使用的是Chroma,它是一个轻量级向量数据库,拥有丰富的功能和简单的 API,具有简单、易用、轻量的优点,但功能相对简单且不支持GPU加速。
1.1 数据预处理
首先在项目目录下面新建一个文件夹/data_base/knowledge_db,把用到的资料放进knowledge_db里。
1.1.1 数据加载读取
首先来读取数据,由于我的知识库里文本类型是PDF和Markdown文件,我们可以使用 LangChain 的 PyMuPDFLoader 来读取知识库的 PDF 文件,用UnstructuredMarkdownLoader来读取Markdown文件。
首先看PDF文件的加载:
from langchain.document_loaders.pdf import