哪些网上订餐的网站做的好,免费wordpress域名能绑定吗,《网站建设与维护》讲义,2022年免费网站软件下载LangChain的介绍和入门 1 什么是LangChain LangChain由 Harrison Chase 创建于2022年10月#xff0c;它是围绕LLMs#xff08;大语言模型#xff09;建立的一个框架#xff0c;LLMs使用机器学习算法和海量数据来分析和理解自然语言#xff0c;GPT3.5、GPT4是LLMs最先进的代…LangChain的介绍和入门 1 什么是LangChain LangChain由 Harrison Chase 创建于2022年10月它是围绕LLMs大语言模型建立的一个框架LLMs使用机器学习算法和海量数据来分析和理解自然语言GPT3.5、GPT4是LLMs最先进的代表国内百度的文心一言、阿里的通义千问也属于LLMs。LangChain自身并不开发LLMs它的核心理念是为各种LLMs实现通用的接口把LLMs相关的组件“链接”在一起简化LLMs应用的开发难度方便开发者快速地开发复杂的LLMs应用。LangChain目前有两个语言的实现Python和Node.js 我们从两个方面全面介绍LangChain一个是LangChain组件的基本概念和应用另一个是LangChain常见的使用场景。 2 LangChain主要组件 一个LangChain的应用是需要多个组件共同实现的LangChain主要支持6种组件
Models模型各种类型的模型和模型集成比如GPT-4Prompts提示包括提示管理、提示优化和提示序列化Memory记忆用来保存和模型交互时的上下文状态Indexes索引用来结构化文档以便和模型交互Chains链一系列对各种组件的调用Agents代理决定模型采取哪些行动执行并且观察流程直到完成为止 2.1 Models
现在市面上的模型多如牛毛各种各样的模型不断出现LangChain模型组件提供了与各种模型的集成并为所有模型提供一个精简的统一接口。
LangChain目前支持三种类型的模型LLMs、Chat Models(聊天模型)、Embeddings Models(嵌入模型. LLMs: 大语言模型接收文本字符作为输入返回的也是文本字符. 聊天模型: 基于LLMs, 不同的是它接收聊天消(一种特定格式的数据)作为输入返回的也是聊天消息. 文本嵌入模型: 文本嵌入模型接收文本作为输入, 返回的是浮点数列表.
LangChain支持的三类模型它们的使用场景不同输入和输出不同开发者需要根据项目需要选择相应。 2.1.1 LLMs (大语言模型)
LLMs使用场景最多常用大模型的下载库https://huggingface.co/models
接下来我们以GPT模型为例, 使用该类模型的组件
第一步安装必备的工具包langchain和openai
pip install openai0.28
pip install langchain注意在使用openai模型之前必须开通OpenAI API服务需要获得API Token。 第二步申请API Token第三部代码实现
# 导入OpenAI模型
from langchain.llms import OpenAI
import os
os.environ[OPENAI_API_KEY] 你的OpenAI API token
llm OpenAI(model_nametext-davinci-003, n2, temperature0.3)
llm(给我讲一个笑话)
# 答案一个猴子去河里洗澡洗完后他看见自己的影子他觉得自己太瘦了于是他又把头放进河里洗了一遍# 使用generate方法可以同时接收多个输入并且返回token使用信息
llm.generate([给我讲一个故事, 给我讲一个笑话])
# 答案# generations[
# [Generation(text\n\n一个叫玛丽的小女孩有一只叫毛毛的小猫。\n\n每天晚上玛丽都会和毛毛一起玩耍一起跳舞一起唱歌一起玩游戏。\n\n有一天玛丽和毛毛一起去海边玩突然毛毛被一只海鸥抓走了。玛丽非常伤心她跑到海边哭了起来哭着喊着毛毛的,
# generation_info{finish_reason: length, logprobs: None}),
# Generation(text\n\n一个叫小明的男孩他很喜欢探险。有一天他和他的朋友们一起去森林里玩突然他发现一个洞穴他非常好奇于是他决定去看看洞穴里面到底有什么。\n\n他走进洞穴里面黑暗而又潮湿他继续前行突然他看到一只大老虎它正在吃一只小兔子。,
# generation_info{finish_reason: length, logprobs: None})],
# [Generation(text\n\n两个熊在森林里走一个熊说“嘿你知道为什么树林里没有路吗”另一个熊回答“不知道为什么”第一个熊说“因为它们都在绕树林跑”, generation_info{finish_reason: stop, logprobs: None}), Generation(text\n\n两个熊在森林里拔萝卜一个熊拔出一个萝卜另一个熊说“你拔的太慢了我拔的快一点”,
# generation_info{finish_reason: stop, logprobs: None})]2.1.2 Chat Models (聊天模型)
聊天消息包含下面几种类型使用时需要按照约定传入合适的值
AIMessage: 用来保存LLM的响应以便在下次请求时把这些信息传回给LLM.HumanMessage: 发送给LLMs的提示信息比如“实现一个快速排序方法”.SystemMessage: 设置LLM模型的行为方式和目标。你可以在这里给出具体的指示比如“作为一个代码专家”或者“返回json格式”.ChatMessage: ChatMessage可以接收任意形式的值但是在大多数时间我们应该使用上面的三种类型.
LangChain支持的常见聊天模型有
模型描述ChatOpenAIOpenAI聊天模型AzureChatOpenAIAzure提供的OpenAI聊天模型PromptLayerChatOpenAI基于OpenAI的提示模版平台
举例说明
from langchain.chat_models import ChatOpenAI
from langchain.schema import (AIMessage,HumanMessage,SystemMessage
)
import os
os.environ[OPENAI_API_KEY] sk-cZ1YYouaq6IVLsj0BOhUT3BlbkFJCcYUOm2imvn1oZMi2NjVchat ChatOpenAI(temperature0)messages [SystemMessage(content返回json object不要纯文本按照每项参数拆分不要说明和解释信息),HumanMessage(content告诉我model Y汽车的尺寸参数)
]print(chat(messages))
# 答案# content{\n 车长: 4,750 mm,\n 车宽: 1,921 mm,\n 车高: 1,624 mm,\n 轴距: 2,890 mm,\n 最小离地间隙: 162 mm,\n 行李箱容积: 1,900 L\n} additional_kwargs{} exampleFalse2.1.3 提示模板
在上面的例子中模型默认是返回纯文本结果的如果需要返回json格式需要不断优化SystemMessage。那么有什么简单的方式快速让模型返回想要的数据呢就是提示模版。
提示模板就是把一些常见的提示整理成模板用户只需要修改模板中特定的词语就能快速准确地告诉模型自己的需求。我们看个例子
第一步导入依赖
from langchain.chat_models import ChatOpenAI
from langchain.prompts import (ChatPromptTemplate,PromptTemplate,SystemMessagePromptTemplate,AIMessagePromptTemplate,HumanMessagePromptTemplate,
)
from langchain.schema import (AIMessage,HumanMessage,SystemMessage
)第二步实现提示模板
system_template你是一个把{input_language}翻译成{output_language}的助手
system_message_prompt SystemMessagePromptTemplate.from_template(system_template)
human_template{text}
human_message_prompt HumanMessagePromptTemplate.from_template(human_template)chat_prompt ChatPromptTemplate.from_messages([system_message_prompt, human_message_prompt])
messages chat_prompt.format_prompt(input_language英语, output_language汉语, textI love programming.)print(messages)
#messages[SystemMessage(content你是一个把英语翻译成汉语的助手, additional_kwargs{}), HumanMessage(contentI love programming., additional_kwargs{}, exampleFalse)]
chat ChatOpenAI(temperature0)print(chat(messages.to_messages()))# content我喜欢编程。 additional_kwargs{} exampleFalse2.1.4 Embeddings Models(嵌入模型) Embeddings Models特点将字符串作为输入返回一个浮动数的列表。在NLP中Embedding的作用就是将数据进行文本向量化。
Embeddings Models可以为文本创建向量映射这样就能在向量空间里去考虑文本执行诸如语义搜索之类的操作比如说寻找相似的文本片段。
接下来我们以一个OpenAI文本嵌入模型的例子进行说明
from langchain.embeddings import OpenAIEmbeddings
open_embed OpenAIEmbeddings()
text 这是一个测试文档。query_result open_embed.embed_query(text)
doc_result open_embed.embed_documents([text])print(query_result)
# [-0.009422866627573967, 0.004315766040235758, 0.002380653750151396, ...]上述代码中我们分别使用了两种方法来进行文本的向量表示他们最大不同在于embed_query()接收一个字符串的输入而embed_documents可以接收一组字符串。
LangChain集成的文本嵌入模型有
AzureOpenAI、Cohere、Hugging Face Hub、OpenAI、Llama-cpp、SentenceTransformers
2.2 Prompts
Prompt是指当用户输入信息给模型时加入的提示这个提示的形式可以是zero-shot或者few-shot等方式目的是让模型理解更为复杂的业务场景以便更好的解决问题。
提示模板如果你有了一个起作用的提示你可能想把它作为一个模板用于解决其他问题LangChain就提供了PromptTemplates组件它可以帮助你更方便的构建提示。
zero-shot提示方式
from langchain import PromptTemplate
from langchain.llms import OpenAItemplate 我的邻居姓{lastname}他生了个儿子给他儿子起个名字prompt PromptTemplate(input_variables[lastname],templatetemplate,
)prompt_text prompt.format(lastname王)
# result: 我的邻居姓王他生了个儿子给他儿子起个名字# 调用OpenAI
llm OpenAI(temperature0.9)
print(llm(prompt_text))# 叫王爱慕。few-shot提示方式
from langchain import PromptTemplate, FewShotPromptTemplate
from langchain.llms import OpenAIexamples [{word: 开心, antonym: 难过},{word: 高, antonym: 矮},
]example_template
单词: {word}
反义词: {antonym}\\n
example_prompt PromptTemplate(input_variables[word, antonym],templateexample_template,
)few_shot_prompt FewShotPromptTemplate(examplesexamples,example_promptexample_prompt,prefix给出每个单词的反义词,suffix单词: {input}\\n反义词:,input_variables[input],example_separator\\n,
)prompt_text few_shot_prompt.format(input粗)
print(prompt_text)# 给出每个单词的反义词
# 单词: 开心
# 反义词: 难过# 单词: 高
# 反义词: 矮# 单词: 粗
# 反义词:# 调用OpenAI
llm OpenAI(temperature0.9)
print(llm(prompt_text))# 细2.3 Chains(链)
在LangChain中Chains描述了将LLM与其他组件结合起来完成一个应用程序的过程.
针对上一小节的提示模版例子zero-shot里面我们可以用链来连接提示模版组件和模型进而可以实现代码的更改
from langchain import PromptTemplate
from langchain.llms import OpenAI
from langchain.chains import LLMChain
# 定义模板
template 我的邻居姓{lastname}他生了个儿子给他儿子起个名字prompt PromptTemplate(input_variables[lastname],templatetemplate,
)
llm OpenAI(temperature0.9)chain LLMChain(llm llm, prompt prompt)
# 执行链
print(chain.run(王))
# 可以叫王子也可以叫小王或者小王子等。。如果你想将第一个模型输出的结果直接作为第二个模型的输入还可以使用LangChain的SimpleSequentialChain, 代码如下
from langchain import PromptTemplate
from langchain.llms import OpenAI
from langchain.chains import LLMChain, SimpleSequentialChain
# 创建第一条链
template 我的邻居姓{lastname}他生了个儿子给他儿子起个名字first_prompt PromptTemplate(input_variables[lastname],templatetemplate,
)
llm OpenAI(temperature0.9)first_chain LLMChain(llm llm, prompt first_prompt)# 创建第二条链
second_prompt PromptTemplate(input_variables[child_name],template邻居的儿子名字叫{child_name}给他起一个小名,
)second_chain LLMChain(llmllm, promptsecond_prompt)# 链接两条链
overall_chain SimpleSequentialChain(chains[first_chain, second_chain], verboseTrue)# 执行链只需要传入第一个参数
catchphrase overall_chain.run(王)2.4 Agents (代理)
在 LangChain 中 Agents 的作用就是根据用户的需求来访问一些第三方工具(比如搜索引擎或者数据库)进而来解决相关需求问题。
为什么要借助第三方库
因为大模型虽然非常强大但是也具备一定的局限性比如不能回答实时信息、处理数学逻辑问题仍然非常的初级等等。因此可以借助第三方工具来辅助大模型的应用。 几个重要的概念 代理 负责控制整段代码的逻辑和执行代理暴露了一个接口用来接收用户输入并返回AgentAction或AgentFinish。AgentAction决定使用哪个工具AgentFinish意味着代理的工作完成了返回给用户结果。 工具 第三方服务的集成比如谷歌、bing等等 工具包 一些集成好了代理包比如create_csv_agent 可以使用模型解读csv文件。 模型解决csv文件示例 from langchain.agents import create_csv_agent
from langchain.llms import OpenAI
agent create_csv_agent(OpenAI(temperature0), data.csv, verboseTrue)
agent.run(一共有多少行数据?)代理执行器: 负责迭代运行代理的循环直到满足停止的标准。 现在我们实现一个使用代理的例子假如我们在北京想让大语言模型告诉我们明天穿什么衣服由于大语言模型不知道明天的天气我们借助于serpapi 来查询天气并传递给模型代码如下
from langchain.agents import load_tools
from langchain.agents import initialize_agent
from langchain.agents import AgentType
from langchain.llms import OpenAIllm OpenAI(temperature0)
tools load_tools([serpapi], llmllm)
agent initialize_agent(tools, llm, agentAgentType.ZERO_SHOT_REACT_DESCRIPTION, verboseTrue)agent.run(明天在北京穿什么衣服合适?)要注意的是运行这个示例需要申请serpapi token并且设置到环境变量SERPAPI_API_KEY 然后安装依赖包google-search-results LangChain支持的工具如下
工具描述Bing SearchBing搜索Google SearchGoogle搜索Google Serper API一个从google搜索提取数据的APIPython REPL执行python代码Requests执行python代码
2.5 Memory
大模型本身不具备上下文的概念它并不保存上次交互的内容ChatGPT之所以能够和人正常沟通对话因为它进行了一层封装将历史记录回传给了模型。
因此 LangChain 也提供了Memory组件, Memory分为两种类型短期记忆和长期记忆。短期记忆一般指单一会话时传递数据长期记忆则是处理多个会话时获取和更新信息。
目前的Memory组件只需要考虑ChatMessageHistory。举例分析
from langchain.memory import ChatMessageHistoryhistory ChatMessageHistory()
history.add_user_message(在吗)
history.add_ai_message(有什么事?)print(history.messages)# [HumanMessage(content在吗, additional_kwargs{}), AIMessage(content有什么事?, additional_kwargs{})]和OpenAI结合直接使用ConversationChain
from langchain import ConversationChain
from langchain.llms import OpenAIllm OpenAI(temperature0)
conversation ConversationChain(llmllm, verboseTrue)
conversation.predict(input小明有1只猫)
conversation.predict(input小刚有2只狗)
conversation.predict(input小明和小刚一共有几只宠物?)如果要像chatGPT一样长期保存历史消息可以使用messages_to_dict 方法
from langchain.memory import ChatMessageHistory
from langchain.schema import messages_from_dict, messages_to_dicthistory ChatMessageHistory()
history.add_user_message(hi!)
history.add_ai_message(whats up?)dicts messages_to_dict(history.messages)print(dicts)
# [{type: human, data: {content: hi!, additional_kwargs: {}}},
# {type: ai, data: {content: whats up?, additional_kwargs: {}}}]
# 读取历史消息
new_messages messages_from_dict(dicts)print(new_messages)
#[HumanMessage(contenthi!, additional_kwargs{}),
# AIMessage(contentwhats up?, additional_kwargs{})]2.6 Indexes (索引) Indexes组件的目的是让LangChain具备处理文档处理的能力包括文档加载、检索等。注意这里的文档不局限于txt、pdf等文本类内容还涵盖email、区块链、视频等内容。
Indexes组件主要包含类型
文档加载器文本分割器VectorStores检索器 2.6.1 文档加载器
文档加载器主要基于Unstructured 包Unstructured 是一个python包可以把各种类型的文件转换成文本。
文档加载器使用起来很简单只需要引入相应的loader工具
from langchain.document_loaders import TextLoader
loader TextLoader(../state_of_the_union.txt, encodingutf8)
documents loader.load()LangChain支持的文档加载器 (部分)
文档加载器描述CSVCSV问价JSON Files加载JSON文件Jupyter Notebook加载notebook文件Markdown加载markdown文件Microsoft PowerPoint加载ppt文件PDF加载pdf文件Images加载图片File Directory加载目录下所有文件HTML网页
2.6.2 文档分割器
由于模型对输入的字符长度有限制我们在碰到很长的文本时需要把文本分割成多个小的文本片段。
文本分割最简单的方式是按照字符长度进行分割但是这会带来很多问题比如说如果文本是一段代码一个函数被分割到两段之后就成了没有意义的字符所以整体的原则是把语义相关的文本片段放在一起。
LangChain中最基本的文本分割器是CharacterTextSplitter 它按照指定的分隔符默认“\n\n”进行分割并且考虑文本片段的最大长度。我们看个例子
from langchain.text_splitter import CharacterTextSplitter# 初始字符串
state_of_the_union ...text_splitter CharacterTextSplitter( separator \\n\\n,chunk_size 1000,chunk_overlap 200,length_function len,
)texts text_splitter.create_documents([state_of_the_union])除了CharacterTextSplitter分割器LangChain还支持其他文档分割器 (部分)
文档加载器描述LatexTextSplitter沿着Latex标题、标题、枚举等分割文本。MarkdownTextSplitter沿着Markdown的标题、代码块或水平规则来分割文本。TokenTextSplitter根据openAI的token数进行分割PythonCodeTextSplitter沿着Python类和方法的定义分割文本。
2.6.3 VectorStores
VectorStores是一种特殊类型的数据库它的作用是存储由嵌入创建的向量提供相似查询等功能。我们使用其中一个Chroma 组件作为例子
from langchain.embeddings.openai import OpenAIEmbeddings
from langchain.text_splitter import CharacterTextSplitter
from langchain.vectorstores import Chroma# pku.txt内容https://www.pku.edu.cn/about.html
with open(./pku.txt) as f:state_of_the_union f.read()
text_splitter CharacterTextSplitter(chunk_size100, chunk_overlap0)
texts text_splitter.split_text(state_of_the_union)embeddings OpenAIEmbeddings()docsearch Chroma.from_texts(texts, embeddings)query 1937年北京大学发生了什么
docs docsearch.similarity_search(query)
print(docs)LangChain支持的VectorStore如下
VectorStore描述Chroma一个开源嵌入式数据库ElasticSearchElasticSearchMilvus用于存储、索引和管理由深度神经网络和其他机器学习ML模型产生的大量嵌入向量的数据库Redis基于redis的检索器FAISSFacebook AI相似性搜索服务Pinecone一个具有广泛功能的向量数据库
2.6.4 检索器
检索器是一种便于模型查询的存储数据的方式LangChain约定检索器组件至少有一个方法get_relevant_texts这个方法接收查询字符串返回一组文档。
from langchain.document_loaders import TextLoader
from langchain.text_splitter import CharacterTextSplitter
from langchain.vectorstores import FAISS
from langchain.embeddings import OpenAIEmbeddingsloader TextLoader(../../../state_of_the_union.txt)
documents loader.load()
text_splitter CharacterTextSplitter(chunk_size1000, chunk_overlap0)
texts text_splitter.split_documents(documents)
embeddings OpenAIEmbeddings()db FAISS.from_documents(texts, embeddings)
retriever db.as_retriever()
docs retriever.get_relevant_documents(what did he say about ketanji brown jackson)LangChain支持的检索器组件如下
检索器介绍Azure Cognitive Search RetrieverAmazon ACS检索服务ChatGPT Plugin RetrieverChatGPT检索插件DataberryDataberry检索ElasticSearch BM25ElasticSearch检索器MetalMetal检索器Pinecone Hybrid SearchPinecone检索服务SVM RetrieverSVM检索器TF-IDF RetrieverTF-IDF检索器VectorStore RetrieverVectorStore检索器Vespa retriever一个支持结构化文本和向量搜索的平台Weaviate Hybrid Search一个开源的向量搜索引擎Wikipedia支持wikipedia内容检索
3 LangChain使用场景 个人助手基于文档的问答系统聊天机器人Tabular数据查询API交互信息提取文档总结 小结
主要对LangChain框架基础知识介绍我们对LangChain有一个初步认识了解LangChain的使用场景。