返回文章列表

LangChain文字分割與嵌入技術詳解

本文深入探討 LangChain 中的文字分割和嵌入技術,包含 CharacterTextSplitter、RecursiveCharacterTextSplitter 和 CodeTextSplitter 等工具的應用,以及向量儲存、文字嵌入模型和快取嵌入的實踐。透過 Python

自然語言處理 程式開發

LangChain 提供了多種文字分割工具,例如 CharacterTextSplitter 和 RecursiveCharacterTextSplitter,可以根據需求靈活地將長文字分割成小塊,以便於後續處理。向量儲存技術允許將文字轉換為向量形式,並進行高效的相似度搜尋和比較。文字嵌入模型則可以將文字轉換為向量表示,方便進行語義分析和理解。此外,快取嵌入技術可以有效地避免重複計算,節省時間和資源。這些技術的結合,為自然語言處理和程式碼分析等領域提供了強大的工具,可以有效地處理大規模文字資料,提高分析效率和準確性。

完整工作範例:文字分割

以下是使用 CharacterTextSplitter 進行文字分割的完整工作範例:

import langchain_text_splitters

# 載入檔案
with open("./sample_data/The Art of Money Getting.txt") as f:
    art_of_money_getting = f.read()

# 建立文字分割器
text_splitter = langchain_text_splitters.CharacterTextSplitter(
    separator="\n\n",
    chunk_size=1000,
    chunk_overlap=200,
    length_function=len,
    is_separator_regex=False
)

# 分割檔案
documents = text_splitter.create_documents([art_of_money_getting])

# 列印第五個檔案
print(documents[4])

這個範例示範瞭如何使用 CharacterTextSplitter 將長篇檔案分割成較小的塊,並列印第五個檔案的內容和元資料。

測試文字分割器

要測試文字分割器的效果,可以使用 Chunkviz 工具。這個工具允許您微調分割引數,以達到最佳的效果。

遞迴分割

遞迴分割是一種將文字分割成塊的方法,使用遞迴方式將文字分割成較小的塊。這種方法可以保證塊的大小更均勻,尤其是在處理長篇檔案時。

以下是遞迴分割的範例:

from langchain_text_splitters import RecursiveCharacterTextSplitter

text = "This is a sample text. It consists of multiple sentences. Some sentences are longer than others. We will split this text into chunks."

這個範例示範瞭如何使用 RecursiveCharacterTextSplitter 將文字分割成塊,並保證塊的大小更均勻。

文字分割器的應用

在自然語言處理(NLP)中,文字分割是一種常見的技術,用於將長篇文字分割成更小的塊,以便於分析和處理。以下,我們將介紹兩種文字分割器:CharacterTextSplitterRecursiveCharacterTextSplitter

CharacterTextSplitter

CharacterTextSplitter 是一種基礎的文字分割器,它根據指定的分隔符和塊大小將文字分割成更小的塊。下面是其使用範例:

text_splitter = CharacterTextSplitter(separator=". ", chunk_size=30, chunk_overlap=5)
documents = text_splitter.create_documents([text])

print("CharacterTextSplitter:")
for doc in documents:
    print(doc.page_content)
    print("
---
")

在這個範例中,CharacterTextSplitter 將文字分割成塊大小為 30 個字元的塊,並且每個塊之間有 5 個字元的重疊。

RecursiveCharacterTextSplitter

RecursiveCharacterTextSplitter 是一種更先進的文字分割器,它可以根據多個分隔符和塊大小將文字分割成更小的塊。下面是其使用範例:

recursive_text_splitter = RecursiveCharacterTextSplitter(separators=[". ", "! ", "? "], chunk_size=30, chunk_overlap=5)
recursive_documents = recursive_text_splitter.create_documents([text])

print("RecursiveCharacterTextSplitter:")
for doc in recursive_documents:
    print(doc.page_content)
    print("
---
")

在這個範例中,RecursiveCharacterTextSplitter 將文字分割成塊大小為 30 個字元的塊,並且每個塊之間有 5 個字元的重疊。同時,它也可以根據多個分隔符(. , ! , ? )進行分割。

內容解密:

在上述範例中,CharacterTextSplitterRecursiveCharacterTextSplitter 都可以將長篇文字分割成更小的塊,以便於分析和處理。然而,RecursiveCharacterTextSplitter 更加先進,因為它可以根據多個分隔符和塊大小進行分割。

圖表翻譯:

以下是 CharacterTextSplitterRecursiveCharacterTextSplitter 的工作流程圖:

在這個圖表中,CharacterTextSplitterRecursiveCharacterTextSplitter 都可以將長篇文字分割成更小的塊,並且輸出結果。然而,RecursiveCharacterTextSplitter 更加先進,因為它可以根據多個分隔符和塊大小進行分割。

文字分割技術深度剖析

在自然語言處理(NLP)和程式碼分析中,文字分割是一個至關重要的步驟。它能夠將長篇文字或程式碼分割成小塊,以便於分析、理解和處理。玄貓將帶領您深入探討文字分割的世界,包括其原理、應用和實踐。

文字分割的挑戰

文字分割面臨著多個挑戰,包括如何確定合適的分割點、如何處理長篇文字或程式碼、以及如何保證分割結果的品質。傳統的文字分割方法往往依賴於簡單的分割規則,例如以句號或換行符為分割點。但是,這種方法並不能滿足所有的情況,特別是在面對複雜的文字或程式碼時。

文字分割演算法

為了克服傳統方法的侷限性,玄貓將介紹兩種先進的文字分割演算法:CharacterTextSplitter 和 RecursiveCharacterTextSplitter。這兩種演算法能夠根據指定的分割規則和文字特點進行分割,從而獲得更好的分割結果。

CharacterTextSplitter

CharacterTextSplitter 是一種根據字元的文字分割演算法。它根據指定的分割規則(例如句號或換行符)將文字分割成小塊。這種演算法簡單易行,但可能不適合長篇文字或程式碼。

RecursiveCharacterTextSplitter

RecursiveCharacterTextSplitter 是一種遞迴的文字分割演算法。它不僅能夠根據指定的分割規則進行分割,而且還能夠遞迴地分割那些超過指定大小限制的文字塊。這種演算法能夠獲得更均勻的分割結果,特別是在面對長篇文字或程式碼時。

程式碼分割技術

除了文字分割,程式碼分割也是另一個重要的研究領域。玄貓將介紹 CodeTextSplitter,一種專門為程式碼設計的分割演算法。這種演算法能夠根據程式語言的結構和語法進行分割,從而獲得更好的分割結果。

CodeTextSplitter

CodeTextSplitter 是一種根據程式語言的程式碼分割演算法。它能夠根據程式語言的結構和語法進行分割,從而獲得更好的分割結果。這種演算法可以應用於多個領域,包括程式碼分析、程式碼搜尋和程式碼檔案生成。

實踐和應用

玄貓將透過實際例子展示如何使用 CharacterTextSplitter、RecursiveCharacterTextSplitter 和 CodeTextSplitter 進行文字和程式碼分割。這些例子將展示如何使用這些演算法獲得更好的分割結果,並如何應用於實際問題中。

from langchain_text_splitters import CodeTextSplitter

code_snippet = '''
def greet(name):
    print(f"Hello, {name}!")

def main():
    name = input("Enter your name: ")
    greet(name)

if __name__ == "__main__":
    main()
'''

code_splitter = CodeTextSplitter(language="python", chunk_size=50, chunk_overlap=0)
code_chunks = code_splitter.create_documents([code_snippet])

for chunk in code_chunks:
    print(chunk.page_content)

圖表翻譯:

程式碼分割器的應用

程式碼分割器(CodeTextSplitter)是一種工具,能夠將程式碼分割成邏輯單元,以便於分析和理解。以下是一個使用 Python 的範例:

def greet(name):
    print(f"Hello, {name}!")

def main():
    name = input("Enter your name: ")
    greet(name)

if __name__ == "__main__":
    main()

在這個範例中,程式碼被分割成三個邏輯單元:greet函式、main函式和主程式入口。

文字分割器的應用

文字分割器(TextSplitter)是一種工具,能夠將文字分割成小塊,以便於處理和分析。以下是一個使用 Python 的範例:

from langchain_text_splitters import RecursiveCharacterTextSplitter

# 載入知識函式庫文章
with open("returns_policy.txt") as f:
    returns_policy = f.read()

# 建立一個RecursiveCharacterTextSplitter例項
text_splitter = RecursiveCharacterTextSplitter.from_tiktoken_encoder(
    model_name="gpt-3.5-turbo",  # 指定語言模型
    chunk_size=500,  # 設定所需的chunk大小(以token為單位)
    chunk_overlap=50,  # 允許chunk之間有一定的重疊度,以保留上下文
)

在這個範例中,文字分割器被用來將知識函式庫文章分割成小塊,以便於訓練語言模型。

內容解密:

程式碼分割器和文字分割器都是用來分割程式碼和文字成小塊的工具。程式碼分割器可以將程式碼分割成邏輯單元,以便於分析和理解。文字分割器可以將文字分割成小塊,以便於處理和分析。

圖表翻譯:

此圖表展示了程式碼和文字如何被分割成小塊,以便於分析和理解。

圖表翻譯:

圖表展示了程式碼和文字的分割過程。程式碼被分割成邏輯單元,而文字被分割成小塊。這些小塊可以被用來訓練語言模型或進行其他分析。

文字分割和向量儲存

在處理大規模文字資料時,將文字分割成小塊是非常重要的。這樣不僅可以提高搜尋效率,還可以使得文字更容易被理解和分析。下面,我們將介紹如何使用 RecursiveCharacterTextSplitter 進行文字分割,並探討向量儲存的概念和應用。

文字分割

首先,我們需要將文字分割成小塊。這可以使用 RecursiveCharacterTextSplitter 實作。以下是示例程式碼:

from langchain.text_splitter import RecursiveCharacterTextSplitter

# 建立一個RecursiveCharacterTextSplitter例項
text_splitter = RecursiveCharacterTextSplitter.from_tiktoken_encoder("gpt-3.5-turbo", chunk_size=500, chunk_overlap=50)

# 將文字分割成小塊
chunks = text_splitter.split_text(returns_policy)

# 列印分割後的文字塊數
print(f"Number of chunks: {len(chunks)}")

# 列印第一個文字塊
print("First chunk:")
print(chunks[0])

在這個示例中,我們建立了一個 RecursiveCharacterTextSplitter 例項,指定了語言模型和分割引數。然後,我們使用split_text方法將文字分割成小塊,並列印預出分割後的文字塊數和第一個文字塊。

向量儲存

向量儲存是一種特殊的資料儲存格式,允許快速和高效地搜尋和比較資料。向量儲存的工作原理是將資料轉換成向量形式,這樣可以方便地計算相似度和進行搜尋。

以下是向量儲存的基本步驟:

  1. 載入源資料:首先,需要載入源資料到向量儲存中。
  2. 查詢向量儲存:然後,可以使用查詢向量儲存來搜尋最相似的專案。
  3. 檢索最相似專案:向量儲存傳回最相似的專案,類別似於搜尋引擎傳回的結果。

文字嵌入模型

文字嵌入模型是一種將文字轉換成向量形式的技術,允許快速和高效地搜尋和比較文字。文字嵌入模型的工作原理是將文字轉換成向量形式,這樣可以方便地計算相似度和進行搜尋。

以下是文字嵌入模型的基本步驟:

  1. 載入文字資料:首先,需要載入文字資料到文字嵌入模型中。
  2. 轉換為向量:然後,需要將文字轉換成向量形式。
  3. 搜尋和比較:最後,可以使用向量形式的文字進行搜尋和比較。

實踐應用

下面是一個使用文字嵌入模型進行搜尋和比較的實踐應用:

from langchain_openai import OpenAIEmbeddings

# 建立一個OpenAIEmbeddings例項
embeddings_model = OpenAIEmbeddings()

# 定義一個客戶評價列表
reviews = [
    "這個產品很好用!",
    "我不喜歡這個產品。",
    "這個產品的品質很好。"
]

# 將客戶評價轉換為向量
vectors = embeddings_model.embed(reviews)

# 搜尋和比較
similarities = embeddings_model.similarity(vectors)

在這個示例中,我們建立了一個 OpenAIEmbeddings 例項,定義了一個客戶評價列表,將客戶評價轉換為向量,並使用similarity方法進行搜尋和比較。

圖表翻譯:

@startuml
skinparam backgroundColor #FEFEFE
skinparam componentStyle rectangle

title LangChain文字分割與嵌入技術詳解

package "機器學習流程" {
    package "資料處理" {
        component [資料收集] as collect
        component [資料清洗] as clean
        component [特徵工程] as feature
    }

    package "模型訓練" {
        component [模型選擇] as select
        component [超參數調優] as tune
        component [交叉驗證] as cv
    }

    package "評估部署" {
        component [模型評估] as eval
        component [模型部署] as deploy
        component [監控維護] as monitor
    }
}

collect --> clean : 原始資料
clean --> feature : 乾淨資料
feature --> select : 特徵向量
select --> tune : 基礎模型
tune --> cv : 最佳參數
cv --> eval : 訓練模型
eval --> deploy : 驗證模型
deploy --> monitor : 生產模型

note right of feature
  特徵工程包含:
  - 特徵選擇
  - 特徵轉換
  - 降維處理
end note

note right of eval
  評估指標:
  - 準確率/召回率
  - F1 Score
  - AUC-ROC
end note

@enduml

這個圖表展示了向量儲存的基本流程,從載入文字資料到輸出結果。

檔案嵌入和查詢嵌入

首先,我們需要將客戶評價檔案嵌入到向量空間中。這可以使用 embed_documents 方法實作。

# 匯入必要的函式庫
from langchain.embeddings import HuggingFaceEmbeddings

# 建立一個 HuggingFaceEmbeddings 例項
embeddings_model = HuggingFaceEmbeddings()

# 客戶評價檔案
reviews = [
    "我絕對喜愛這個產品!它使我的生活變得更加容易,我無法想象回到以前的狀態。",
    "我最初有些懷疑,但是在使用這個服務幾周後,我真的很佩服。客戶支援是頂級的,功能正是我需要的。",
    "我已經使用這個軟體有一段時間了,它確實提高了我的生產力。使用者介面是直觀的,與其他工具的整合是無縫的。",
    "我與這家公司有很好的合作經驗。他們按時交付了專案,品質超出了我的期望。我絕對會再次與他們合作。",
    "我不是完全滿意這個產品。雖然它有一些有用的功能,但我發現它在某些領域缺乏,而且價格似乎有些高。"
]

# 將客戶評價檔案嵌入到向量空間中
embeddings = embeddings_model.embed_documents(reviews)

# 列印嵌入的數量和每個嵌入的長度
print(f"嵌入的數量:{len(embeddings)}")
print(f"每個嵌入的長度:{len(embeddings[0])}")

接下來,我們定義一個查詢文字,詢問客戶評價中提到的正面方面。

# 定義查詢文字
query_text = "客戶評價中提到的正面方面是什麼?"

# 將查詢文字嵌入到向量空間中
embedded_query = embeddings_model.embed_query(query_text)

# 列印嵌入查詢的長度和前五個元素
print(f"嵌入查詢的長度:{len(embedded_query)}")
print(f"嵌入查詢的前五個元素:{embedded_query[:5]}")

快取嵌入

快取嵌入是指儲存或臨時儲存計算出的嵌入,以避免每次需要時都要重新計算。這可以節省時間、金錢和計算資源。

# 匯入必要的函式庫
from langchain.embeddings import CacheBackedEmbeddings
from langchain.storage import LocalFileStore

# 建立一個 LocalFileStore 例項
document_embedding_cache = LocalFileStore()

# 建立一個 CacheBackedEmbeddings 例項
cache_backed_embeddings = CacheBackedEmbeddings(
    underlying_embedder=embeddings_model,
    document_embedding_cache=document_embedding_cache,
    batch_size=32,  # 可選
    namespace="my_namespace"  # 可選
)

程式碼逐步解釋

  1. 安裝或升級必要的包。
  2. 匯入必要的函式庫。
  3. 建立一個 LocalFileStore 例項,用於儲存嵌入。
  4. 建立一個 CacheBackedEmbeddings 例項,用於快取嵌入。
  5. 使用 CacheBackedEmbeddings 例項將客戶評價檔案嵌入到向量空間中。
  6. 將查詢文字嵌入到向量空間中。
  7. 列印嵌入查詢的長度和前五個元素。

注意:這裡只是一個簡單的示例,實際應用中可能需要根據具體情況進行調整和最佳化。

從商業價值視角來看,有效率的文字分割策略能顯著提升自然語言處理應用在企業中的實用性。透過本篇對CharacterTextSplitterRecursiveCharacterTextSplitterCodeTextSplitter 等不同文字分割器的剖析,我們深入理解了如何根據不同文字型別(如一般文章、程式碼)選擇合適的分割策略,並探討了分割粒度、重疊度等關鍵引數的影響。更進一步,文章闡述了文字分割如何與向量儲存、嵌入技術結合,最佳化搜尋效率和語義理解,這對於知識函式庫構建、客戶服務自動化等商業應用至關重要。然而,目前的文字分割技術仍面臨挑戰,例如如何更精確地捕捉語義邊界,避免資訊遺漏或造成上下文斷裂。未來發展方向可能包含結合更進階的語意理解模型,以及針對特定領域(例如法律、醫療)的客製化分割方案。對於企業而言,選擇合適的文字分割策略並持續關注技術演進,才能最大化其商業價值。玄貓認為,掌握這些技術細節,並根據實際業務需求調整引數,才能在競爭激烈的市場中取得優勢。