構建一個檢索增強生成(RAG)應用程序

:::tips
此文檔是LangChain官方教程的實踐總結:
https://python.langchain.com/v0.2/docs/tutorials/rag/
實踐前你需要準備:
OPENAI_API_KEY Generator:根據檢索到的信息和用戶的查詢生成自然語言的回答。
LANGCHAIN_API_KEY 密切監控和評估您的應用程序,以便您可以快速、自信地開發。
py 環境準備(conda)。
:::

簡介

我們將在網站上構建一個 QA 應用程序。我們將使用的具體網站是 Lilian Weng 的 LLM Powered Autonomous Agents 博客文章,該網站允許我們提出有關帖子內容的問題。

一步一步成功

數據收集

我們需要首先加載博客文章內容。為此,我們可以使用 DocumentLoaders,它們是從源加載數據并返回文檔列表的對象。 Document 是一個帶有一些 page_content (str) 和 metadata (dict) 的對象。
在本例中,我們將使用 WebBaseLoader,它使用 urllib 從 Web URL 加載 HTML,并使用 BeautifulSoup 將其解析為文本。我們可以通過 bs_kwargs 將參數傳遞給 BeautifulSoup 解析器來自定義 HTML -> 文本解析(請參閱 BeautifulSoup 文檔)。在這種情況下,只有類為“post-content”、“post-title”或“post-header”的 HTML 標記是相關的,因此我們將刪除所有其他標記。

import bs4
from langchain_community.document_loaders import WebBaseLoader# Only keep post title, headers, and content from the full HTML.
bs4_strainer = bs4.SoupStrainer(class_=("post-title", "post-header", "post-content"))
loader = WebBaseLoader(web_paths=("https://lilianweng.github.io/posts/2023-06-23-agent/",),bs_kwargs={"parse_only": bs4_strainer},
)
docs = loader.load()
len(docs[0].page_content)
43131
print(docs[0].page_content[:500])
######LLM Powered Autonomous AgentsDate: June 23, 2023  |  Estimated Reading Time: 31 min  |  Author: Lilian WengBuilding agents with LLM (large language model) as its core controller is a cool concept. Several proof-of-concepts demos, such as AutoGPT, GPT-Engineer and BabyAGI, serve as inspiring examples. The potentiality of LLM extends beyond generating well-written copies, stories, essays and programs; it can be framed as a powerful general problem solver.
Agent System Overview#
In

數據分塊

我們加載的文檔長度超過 42k 個字符。這太長了,無法適應許多模型的上下文窗口。即使對于那些可以在其上下文窗口中容納完整帖子的模型,模型也可能很難在很長的輸入中找到信息。
為了解決這個問題,我們將把 Document 分割成塊以進行嵌入和向量存儲。這應該可以幫助我們在運行時僅檢索博客文章中最相關的部分。
在本例中,我們將把文檔分成 1000 個字符的塊,塊之間有 200 個字符的重疊。重疊有助于降低將語句與與其相關的重要上下文分開的可能性。我們使用 RecursiveCharacterTextSplitter,它將使用常見的分隔符(如換行符)遞歸地分割文檔,直到每個塊的大小合適。這是針對一般文本用例推薦的文本分割器。
我們設置 add_start_index=True ,以便將初始文檔中每個分割文檔開始的字符索引保留為元數據屬性“start_index”。

from langchain_text_splitters import RecursiveCharacterTextSplittertext_splitter = RecursiveCharacterTextSplitter(chunk_size=1000, chunk_overlap=200, add_start_index=True
)
all_splits = text_splitter.split_documents(docs)
len(all_splits)
66
len(all_splits[0].page_content)
969
all_splits[10].metadata
{'source': 'https://lilianweng.github.io/posts/2023-06-23-agent/','start_index': 7056}

文本嵌入+存儲

現在我們需要為 66 個文本塊建立索引,以便我們可以在運行時搜索它們。最常見的方法是嵌入每個文檔分割的內容并將這些嵌入插入向量數據庫(或向量存儲)中。當我們想要搜索分割時,我們采用文本搜索查詢,將其嵌入,并執行某種“相似性”搜索,以識別與查詢嵌入最相似的嵌入的存儲分割。最簡單的相似性度量是余弦相似性——我們測量每對嵌入(高維向量)之間角度的余弦。
我們可以使用 Chroma 矢量存儲和 OpenAIEmbeddings 模型將所有文檔分割嵌入并存儲在單個命令中。

from langchain_chroma import Chroma
from langchain_openai import OpenAIEmbeddingsvectorstore = Chroma.from_documents(documents=all_splits, embedding=OpenAIEmbeddings())

檢索

現在讓我們編寫實際的應用邏輯。我們想要創建一個簡單的應用程序,它接受用戶問題,搜索與該問題相關的文檔,將檢索到的文檔和初始問題傳遞給模型,然后返回答案。
首先,我們需要定義搜索文檔的邏輯。 LangChain 定義了一個 Retriever 接口,它包裝了一個索引,該索引可以在給定字符串查詢的情況下返回相關的 Documents 。
最常見的 Retriever 類型是 VectorStoreRetriever,它使用向量存儲的相似性搜索功能來促進檢索。任何 VectorStore 都可以通過 VectorStore.as_retriever() 輕松轉換為 Retriever :

retriever = vectorstore.as_retriever(search_type="similarity", search_kwargs={"k": 6})retrieved_docs = retriever.invoke("What are the approaches to Task Decomposition?")
len(retrieved_docs)
6
print(retrieved_docs[0].page_content)
Tree of Thoughts (Yao et al. 2023) extends CoT by exploring multiple reasoning possibilities at each step. It first decomposes the problem into multiple thought steps and generates multiple thoughts per step, creating a tree structure. The search process can be BFS (breadth-first search) or DFS (depth-first search) with each state evaluated by a classifier (via a prompt) or majority vote.
Task decomposition can be done (1) by LLM with simple prompting like "Steps for XYZ.\n1.", "What are the subgoals for achieving XYZ?", (2) by using task-specific instructions; e.g. "Write a story outline." for writing a novel, or (3) with human inputs.

生成

我們使用 gpt-3.5-turbo OpenAI 聊天模型,但任何 LangChain LLM 或 ChatModel 都可以替換。

import osos.environ["OPENAI_API_KEY"] = "your openai api key"from langchain_openai import ChatOpenAIllm = ChatOpenAI(model="gpt-3.5-turbo-0125")

我們使用已簽入 LangChain 提示中心的 RAG 提示。rlm/rag-prompt

from langchain import hubprompt = hub.pull("rlm/rag-prompt")

截屏2024-06-21 下午5.43.23.png

組裝鏈

我們將使用 LCEL Runnable 協議來定義鏈,使我們能夠

  • 以透明的方式將組件和功能連接在一起
  • 在 LangSmith 中自動追蹤我們的鏈條
  • 開箱即用地進行流式、異步和批量呼叫。
import osos.environ["LANGCHAIN_TRACING_V2"] = "true"
os.environ["LANGCHAIN_API_KEY"] = "your langchain api key"
os.environ["OPENAI_API_KEY"] = "your openai api key"from langchain_openai import ChatOpenAIllm = ChatOpenAI(model="gpt-3.5-turbo-0125")
import bs4
from langchain import hub
from langchain_chroma import Chroma
from langchain_community.document_loaders import WebBaseLoader
from langchain_core.output_parsers import StrOutputParser
from langchain_core.runnables import RunnablePassthrough
from langchain_openai import OpenAIEmbeddings
from langchain_text_splitters import RecursiveCharacterTextSplitter# Load, chunk and index the contents of the blog.
loader = WebBaseLoader(web_paths=("https://lilianweng.github.io/posts/2023-06-23-agent/",),bs_kwargs=dict(parse_only=bs4.SoupStrainer(class_=("post-content", "post-title", "post-header"))),
)
docs = loader.load()text_splitter = RecursiveCharacterTextSplitter(chunk_size=1000, chunk_overlap=200)
splits = text_splitter.split_documents(docs)
vectorstore = Chroma.from_documents(documents=splits, embedding=OpenAIEmbeddings())# Retrieve and generate using the relevant snippets of the blog.
retriever = vectorstore.as_retriever()
prompt = hub.pull("rlm/rag-prompt")def format_docs(docs):return "\n\n".join(doc.page_content for doc in docs)rag_chain = ({"context": retriever | format_docs, "question": RunnablePassthrough()}| prompt| llm| StrOutputParser()
)response = rag_chain.invoke("What is Agent System Overview?")print(response)

調用

我詢問了兩個問題

  • What is Task Decomposition?

截屏2024-06-21 下午5.51.09.png

  • What is Agent System Overview?

截屏2024-06-21 下午5.51.30.png

剖析 LCEL(鏈) 以了解發生了什么

首先:這些組件中的每一個( retriever 、 prompt 、 llm 等)都是 Runnable 的實例。這意味著它們實現相同的方法 - 例如同步和異步 .invoke 、 .stream 或 .batch - 這使它們更容易連接在一起。它們可以通過 | 運算符連接到 RunnableSequence(另一個 Runnable)。
當遇到 | 運算符時,LangChain 會自動將某些對象轉換為可運行對象。此處, format_docs 被轉換為 RunnableLambda,帶有 “context” 和 “question” 的字典被轉換為 RunnableParallel。細節并不重要,重要的是每個對象都是一個 Runnable。
讓我們跟蹤輸入問題如何流經上述可運行對象:
正如我們在上面看到的, prompt 的輸入預計是一個帶有鍵 “context” 和 “question” 的字典。因此,該鏈的第一個元素構建了可運行對象,它將根據輸入問題計算這兩個值:

  • retriever | format_docs 將問題傳遞給檢索器,生成Document對象,然后傳遞給 format_docs 生成字符串;
  • RunnablePassthrough() 不變地傳遞輸入問題。

然后 chain.invoke(question) 將構建一個格式化的提示,準備進行推理。
最后一步是 llm ,它運行推理,以及 StrOutputParser() ,它只是從 LLM 的輸出消息中提取字符串內容。

遇到的問題

USER_AGENT

截屏2024-06-21 下午6.02.39.png
不阻塞運行,解決方案:
添加下面代碼

user_agent = "MyPythonApp/1.0 (Language=Python/3.9; Platform=Linux/Ubuntu20.04)"
os.environ["USER_AGENT"] = user_agent

SSLError

截屏2024-06-21 下午6.04.49.png
阻塞運行,解決方案:
換個代理。

LangSmith展示

截屏2024-06-21 下午6.09.02.png
截屏2024-06-21 下午6.09.29.png
截屏2024-06-21 下午6.09.52.png

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/34941.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/34941.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/34941.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

【自然語言處理系列】掌握NLP基礎:去停用詞、詞性標注與命名實體識別實戰教程

摘要:本系列教程專注于自然語言處理(NLP)中的基礎元素,包括去停用詞、詞性標注以及命名實體識別。這些步驟是文本預處理和分析不可或缺的組成部分。我們將通過具體的實例和技術演示,講解如何使用Python及其相關庫&…

網絡安全之Windows提權(上篇)(高級進階)

目錄 一,什么是提權? 二,提權的前提 三,如何提權? 1,第一步連接服務器 2,提升權限至iuser?編輯 3,利用補丁漏洞提權至最高級 四,總結 一,什么是提權&am…

大數據集群數據傳輸

簡單的服務器間的通信示例 netcat,簡寫為 nc,是 unix 系統下一個強大的命令行網絡通信工具,用于在兩臺主機之間建立 TCP 或者 UDP 連接,并提供豐富的命令進行數據通信。nc 在網絡參考模型屬于應用層。使用 nc 可以做很多事情&…

docker-compose 之 達夢數據庫(dm8-v202406版)

1、達夢官方沒有提供鏡像直接 pull 的方式,提供的是鏡像的 tar 包,所以需要先去官網下載tar包。 2、然后使用如下 docker load 命令導入鏡像到服務上: docker load -i dm8_20240422_x86_rh6_64_rq_std_8.1.3.100_pack2.tar導入完成后&#…

重磅丨上海容大推出“容聆”智能拾音工牌,賦能線下門店運營數字化

近日,繼豚音營業廳智能質檢終端之后,上海容大數字技術有限公司(簡稱“上海容大”)在線下面對面溝通場景下語音數據采集與智能分析領域取得了新突破,重磅推出AI智能語音工牌產品——“容聆”。 據悉,“容聆”…

mybatis x插件的使用教程(詳細)

MyBatisX 的主要功能 代碼生成: 自動生成 MyBatis 的 Mapper、XML 配置文件和實體類,大大減少手工編寫代碼的工作量。 智能代碼補全: 提供 SQL 語句和 MyBatis 配置的智能代碼補全功能,使開發者能夠更快地編寫代碼。 代碼導航&…

鈾的危害和應用,以及鈾的分離提純

鈾是一種錒系放射性元素,對人體存在一定的危害,如輻射損傷、呼吸系統損傷、神經系統損傷、免疫系統損傷等。 1、輻射損傷:鈾的放射性會對人體產生輻射損傷,長期接觸會增加患癌癥的風險。此外,還可能對人體正常細胞產生…

【網絡安全的神秘世界】解決dvwa靶場報錯:Illegal mix of collations for operation ‘UNION‘

🌝博客主頁:泥菩薩 💖專欄:Linux探索之旅 | 網絡安全的神秘世界 | 專接本 | 每天學會一個滲透測試工具 🚩問題描述 當嘗試執行如下 SQL 語句時: 1 union select schema_name,1 from information_schema.s…

如何挑選護眼燈?一分鐘帶你了解挑選護眼燈的六大準則!

小時候,對正確用眼知識一無所知,也不明白何種光線環境對眼睛最為友善,結果如今的近視度數已瀕臨千度大關。雖然早已習慣佩戴眼鏡的生活,但近視所帶來的諸多不便仍舊在日常生活中無處不在。因此,對于家中孩子的視力健康…

第六十七:iview的select組件在頁面上,下拉數據被遮擋

iview的select組件在頁面上,下拉數據被遮擋 加上**:transfer"true"** 代碼截圖: 官方解說截圖:因為默認值是false 所以要改成:transfer“true”

人工智能水平國際領先,科大訊飛再獲國家科學技術進步獎一等獎

科大訊飛在2023年6月24日榮獲國家科學技術進步獎一等獎,這是對其在多語種智能語音技術及產業化領域取得的突破性成果的高度認可。科大訊飛的這一成就,標志著其在人工智能領域的技術實力和創新能力已達到國際領先水平。 據「TMT星球」了解,科大…

WMV 視頻格式怎么轉換?WMV 視頻為什么不流行了?

目前有越來越多的視頻格式類型,如常見的 MP4、FLV、AVI 等等,而技術的演變也逐漸讓一些常見的視頻格式變的越來越少了。 今天我們一起來聊下 WMV 這個視頻格式,讓我們看看它的發展以及為什么現在越來越少人使用了。 什么是 WMV 視頻格式&…

Git 使用指南(附詳細解釋)

Git 是一個強大的版本控制系統,廣泛用于軟件開發中,用于跟蹤文件的更改、協作工作等。無論你是新手還是有經驗的開發者,掌握 Git 都是非常有益的。這篇博客將帶你了解 Git 的基本使用,希望能幫助你快速入門并有效使用 Git。 1. 創…

論文學習_Nebula: Self-Attention for Dynamic Malware Analysis

論文名稱發表時間發表期刊期刊等級研究單位Nebula: Self-Attention for Dynamic Malware Analysis2024年IEEE TIFSCCF A熱那亞大學1. 引言 研究背景與現存問題:動態惡意軟件分析是一項至關重要的任務,不僅對于檢測而且對于了解整個互聯網上廣泛傳播的威脅而言。 收集樣本后,…

【windows|011】TCP/IP5層模型常見協議及應用總結大全

🍁博主簡介: 🏅云計算領域優質創作者 🏅2022年CSDN新星計劃python賽道第一名 🏅2022年CSDN原力計劃優質作者 ? 🏅阿里云ACE認證高級工程師 ? 🏅阿里云開發者社區專家博主 💊交流社…

記一次面試

Linux查日志,怎么把最后1000行寫到另一個文件中 在Linux中,如果你想要查看日志文件的最后1000行并將其寫入到另一個文件中,你可以使用tail命令。tail命令默認用于輸出文件的最后幾行。 以下是如何使用tail命令將日志文件的最后1000行寫入到另…

java設計模式(二)工廠方法模式(pattern of factory method)

1、模式介紹: 工廠方法模式(pattern of factory method)是一種創建型設計模式,它定義了一個用于創建對象的接口,但將實際創建對象的工作延遲到子類中,這樣可以在不改變整體結構的情況下,通過子…

課時166:腳本發布_腳本技巧_技巧解讀

2.3.1 技巧解讀 學習目標 這一節,我們從 簡單腳本、復雜腳本、注意事項、小結 四個方面來學習 簡單腳本 簡介 1、手工執行的命令一定要可執行2、命令簡單羅列3、固定的內容變量化4、功能函數化復雜腳本 實踐 1、手工執行的命令一定要可執行2、根據發布流程編寫…

第二節課 6月13日 ssh密鑰登陸方式

centos和ubuntu openssh服務的初始安裝 一、實驗:ubuntu系統激活root用戶 ubuntu系統如何激活root用戶,允許root用戶ssh登陸? 1、ubuntu默認root用戶未設置密碼,未激活 激活root用戶,設置root密碼 sudo passwd roo…

vray燈光導致3dmax崩潰怎么解決?

啟動時崩潰 解決方法: 1、兼容模式重新打開 具體步驟:【選中會閃退3dmax版本】——【右鍵“兼容性疑難解答”】——【下一步】——【選擇Windows7/10】——【下一步】——【啟動程序】 啟動完成后,【下一步】——【為我保存這些設置】—完…