数据连接处理流程
数据加载器结构
数据加载器示例 - CSV
LangChain 实现了一个 CSV 加载器,可以将 CSV 文件加载为一系列 Document 对象。CSV 文件的每一行都会被翻译为一个文档。
这里需要自己准备一个csv文件
from langchain_community.document_loaders.csv_loader import CSVLoader
file_path = (
"D:\LangChainM\lang_chain_study\data.csv"
)
loader = CSVLoader(file_path=file_path)
data = loader.load()
for record in data[:2]:
print(record)
--------------------------------------
page_content='name: John
age: 20
city: New York' metadata={'source': 'D:\\LangChainM\\lang_chain_study\\data.csv', 'row': 0}
page_content='name: Jane
age: 25
city: Los Angeles' metadata={'source': 'D:\\LangChainM\\lang_chain_study\\data.csv', 'row': 1}
数据加载器示例-HTML
langchain加载器示例文档连接
# langchain自己的html解析包
pip install "unstructured[html]"
from langchain_community.document_loaders import UnstructuredHTMLLoader
file_path = "..//fake-content.html"
loader = UnstructuredHTMLLoader(file_path)
data = loader.load()
print(data)
# bs4加载html文件
pip install bs4
from langchain_community.document_loaders import BSHTMLLoader
loader = BSHTMLLoader(file_path)
data = loader.load()
print(data)
意味着langchain可以通过构建爬取、解析的workflow(这个后面会讲到),相信随着技术的发展,以后爬虫的编写会越来越简单。
文档转换器
一般加载了文档之后,会对其进行转换,从而更好的适应应用场景。最简单的做法是通过将长文档进行拆分,较小的块可以避免大语言模型对提示词文本长度的限制。而langchain里有许多内置的文档转换器,可以对文档进行拆分、合并、过滤。
文本分割器
这个文本分割器是用于通用文本的推荐工具。它接受一个字符列表作为参数。它会按顺序尝试在这些字符上进行分割,直到块足够小。默认的字符列表是 ["\n\n", "\n", " ", ""]
。这样做的效果是尽可能保持所有段落(然后是句子,再然后是单词)在一起,因为这些通常看起来是语义上相关的文本块。值得注意是,为了保持连贯性,块与块之间是有重复的句子或单词!
pip install -qU langchain-text-splitters
from langchain_text_splitters import RecursiveCharacterTextSplitter
# 加载示例文档
with open("黑神话.txt") as f:
state_of_the_union = f.read()
text_splitter = RecursiveCharacterTextSplitter(
# 设置一个非常小的块大小,只是为了展示。
chunk_size=100,
chunk_overlap=20,
length_function=len,
is_separator_regex=False,
)
texts = text_splitter.create_documents([state_of_the_union])
print(texts[0])
print(texts[1])
文本词嵌入
Embeddings类是一个专为与文本嵌入模型进行交互而设计的类。有许多嵌入模型提供商(如OpenAI、Cohere、Hugging Face等)- 这个类旨在为它们提供一个标准接口。
Embeddings类会为文本创建一个向量表示。这很有用,因为这意味着我们可以在向量空间中思考文本,并做一些类似语义搜索的事情,比如在向量空间中寻找最相似的文本片段。
以上图片中我
和俺
距离就比你
近。
没有代码示例,可以自己探索!
向量存储站
存储和搜索非结构化数据的最常见方式之一是将其嵌入并存储生成的嵌入向量,然后在查询时对非结构化查询进行嵌入,并检索与嵌入查询“最相似”的嵌入向量。向量存储负责存储嵌入数据并为您执行向量搜索。
示例代码(以PDF文件为例)
pip install pypdf
from langchain.document_loaders import PyPDFLoader
loader = PyPDFLoader("C:\\Users\\牧羊少年奇幻之旅.pdf")
documents = loader.load()
len(documents) # pdf有多少页
------------------------------------------------
documents[10] # 第10页内容
Document(metadata={'source': 'C:\\Users\\牧羊少年奇幻之旅.pdf', 'page': 10}, page_content='此,他時不時給⽺群讀⼀些給他留下深刻印象的書籍……\n「你是怎麼學會讀書識字的?」')
# 选择合适的文本分割器,这里我们选择通用型的文本分割器
from langchain.text_splitter import RecursiveCharacterTextSplitter
text_spliter = RecursiveCharacterTextSplitter(
chunk_size = 100,
chunk_overlap = 20,
length_function = len,
)
pages = loader.load_and_split(text_spliter)
print(pages[10])
--------------------------------------------
page_content='有關於煉⾦術的正經刊物問世,我便⽤⼿頭微薄的資⾦購買進⼝書
籍,就像本書中的⼀個⼈物那樣,每天花很多時間去研究煉⾦術複雜
的符號系統。我曾試圖請教⾥約熱內盧兩三位真正致⼒於煉⾦術的研' metadata={'source': 'C:\\Users\\牧羊少年奇幻之旅.pdf', 'page': 3}
# 可以看到经过文本分割器的切割,原本pdf的第三页内容,经过切割成为分割器的第10页内容。成功由大到小。
# 文本词嵌入,这里我们使用的是千帆的包
from langchain.embeddings import QianfanEmbeddingsEndpoint
embeddings_model = QianfanEmbeddingsEndpoint()
embeddings = embeddings_model.embed_documents([pages[10].page_content])
len(embeddings), len(embeddings[0])
embeddings[0]
------------------------------------------
[0.13320407271385193,
0.012875556014478207,
0.10420265048742294,
0.06843224912881851,
-0.006438420154154301,
-0.09219038486480713,
-0.021207181736826897,
-0.005400769412517548,
-0.07586964219808578,
0.08065909147262573,
0.034459590911865234,
0.04865811765193939,
0.06758882105350494,
0.04314351826906204,
-0.04163273051381111,
0.030251313000917435,
-0.0248243510723114,
-0.03728075325489044,
-0.09535235166549683,
0.027110563591122627,
-0.02325417473912239,
-0.030913034453988075,
-0.03559505194425583,
-0.07895366102457047,
0.013680539093911648,
...
0,
0,
0,
-0.03681802377104759,
0]
# 向量存储,我们使用chromadb来进行本地的向量存储
# pip install chromadb
from langchain.embeddings.baidu_qianfan_endpoint import QianfanEmbeddingsEndpoint
from langchain.vectorstores import Chroma
persist_directory = 'C:\\Users\\chroma'
embedding = QianfanEmbeddingsEndpoint()
db = Chroma.from_documents(
documents=pages[:10],
embedding=embedding,
persist_directory=persist_directory
)
# 相似度查询
query = "男孩"
docs = db.similarity_search(query=query)
len(docs)