这里写目录标题
- 利用LangChain构建具备记忆功能的对话检索链
- 设置对话历史记忆
- 构建对话检索链
- 处理问题并生成答案
- 创建基于文档的问答聊天机器人
- 初始设置和导入
- 文档加载和处理
利用LangChain构建具备记忆功能的对话检索链
设置对话历史记忆
为了使问答系统能够记住对话的上下文,我们利用ConversationBufferMemory
类。该类特别设计用于存储交互的历史记录,允许系统引用之前的交流,并针对后续问题提供上下文相关的回答。
# 从langchain.memory模块导入ConversationBufferMemory类
from langchain.memory import ConversationBufferMemory
# 初始化ConversationBufferMemory,设置一个键来存储聊天历史,并配置它返回对话中交换的所有消息
conversation_history_memory = ConversationBufferMemory(
memory_key="conversation_history",
return_messages=True
)
构建对话检索链
设置好记忆组件后,下一步涉及构建对话检索链。这一组件是问答系统的核心,它结合了语言模型、文档检索功能和对话记忆,以处理问题并在对话上下文中生成答案。
# 从langchain.chains模块导入ConversationalRetrievalChain类
from langchain.chains import ConversationalRetrievalChain
# 假设'vector_database'是一个用于文档检索的已初始化向量存储实例
# 将向量数据库转换为与ConversationalRetrievalChain兼容的检索器格式
document_retriever = vector_database.as_retriever()
# 初始化ConversationalRetrievalChain,包含语言模型实例、文档检索器和对话历史记忆组件
question_answering_chain = ConversationalRetrievalChain.from_llm(
language_model=language_model_instance,
retriever=document_retriever,
memory=conversation_history_memory
)
处理问题并生成答案
一旦对话检索链建立起来,系统就可以处理传入的问题,并利用存储的对话历史来生成恰当的答案。
# 定义一个与对话主题相关的问题
initial_question = "概率是不是本课程的基础话题?"
# 通过对话检索链处理问题
initial_result = question_answering_chain({"question": initial_question})
# 从结果中提取并打印答案
print("答案:", initial_result['answer'])
# 继续提出另一个问题,基于初始问题的上下文
follow_up_question = "为什么这些话题被认为是先修课程?"
# 通过对话检索链处理后续问题,利用对话历史来提供上下文
follow_up_result = question_answering_chain({"question": follow_up_question})
# 从结果中提取并打印后续答案
print("答案:", follow_up_result['answer'])
创建基于文档的问答聊天机器人
初始设置和导入
在深入聊天机器人创建过程之前,关键是要导入LangChain中的必要类和模块。这些组件便于文档加载、文本分割、嵌入生成和对话链创建。
# 从LangChain导入类,用于嵌入生成、文本分割、内存内搜索、文档加载、对话链和记忆处理
from langchain.embeddings.openai import OpenAIEmbeddings
from langchain.text_splitter import RecursiveCharacterTextSplitter
from langchain.vectorstores import DocArrayInMemorySearch
from langchain.document_loaders import TextLoader, PyPDFLoader
from langchain.chains import ConversationalRetrievalChain
from langchain.chat_models import ChatOpenAI
文档加载和处理
创建聊天机器人的第一步是从文档加载和处理开始,这涉及读取文档,将其分割成易于处理和检索的小块,然后为每个小块生成嵌入。
def load_documents_and_prepare_database(file_path, chain_type, top_k_results):
"""
从指定文件加载文档,将其分割成易于处理的小块,
为每个小块生成嵌入,并准备向量数据库用于检索。
参数:
- file_path: 文档文件的路径(PDF、文本等)。
- chain_type: 指定要使用的对话链类型。
- top_k_results: 搜索中检索的顶部结果数。
返回:
- 准备好回答问题的对话检索链实例。
"""
# 根据文件类型使用适当的加载器加载文档
document_loader = PyPDFLoader(file_path)
documents = document_loader.load()
# 将文档分割成小块以便更轻松地处理和检索
text_splitter = RecursiveCharacterTextSplitter(chunk_size=1000, chunk_overlap=150)
document_chunks = text_splitter.split_documents(documents)
# 为每个文档小块生成嵌入
embeddings_generator = OpenAIEmbeddings()
vector_database = DocArrayInMemorySearch.from_documents(document_chunks, embeddings_generator)
# 为对话链准备文档检索器
document_retriever = vector_database.as_retriever(search_type="similarity", search_kwargs={"k": top_k_results})
# 使用指定参数初始化对话检索链
chatbot_chain = ConversationalRetrievalChain.from_llm(
llm=ChatOpenAI(model_name='gpt-3.5-turbo', temperature=0),
chain_type=chain_type,
retriever=document_retriever,
return_source_documents=True,
return_generated_question=True,
)
return chatbot_chain