LangChain:文本切割器如何根据tokens拆分文本
大语言模型存在Token数量限制,不应超出该限制(如 GPT-4 Turbo 支持 128K Token)。超出限制会导致截断或报错。
因此,在分割文本成块时,需要计算好Token的数量。市面上存在多种tokenizer,计算文本token数量时,应使用与语言模型相匹配的tokenizer。
官方文档:How to split text by tokens
tiktoken
tiktoken是OpenAI
创建的一个快速BPE
标记器。
我们可以使用 tiktoken来估算会使用到的token数量。对于OpenAI模型来说,这会比较准确。
- 文本如何分割:按传入的字符。
- 如何测量块大小:通过tiktoken标记器。
分割器CharacterTextSplitter, RecursiveCharacterTextSplitter, 和TokenTextSplitter可以被tiktoken直接使用。
安装tiktoken:
1 | %pip install --upgrade --quiet langchain-text-splitters tiktoken |
CharacterTextSplitter
1 | from langchain_text_splitters import CharacterTextSplitter |
执行结果:
1 | 2024年是实现“十四五”规划目标任务的关键一年。中央经济工作会议明确提出稳中求进的工作总基调,要求扎实推动高质量发展。上市公司是加快培育新质生产力的重要载体,肩负着实现高质量发展的时代使命。 |
注意:CharacterTextSplitter
默认的切割符是\n\n
,切割出来的块的大小不是固定的,有可能比设置的限制大。
API指南:CharacterTextSplitter
使用CharacterTextSplitter进行分割,然后使用tiktoken
的.from_tiktoken_encoder()
方法合并块。注意,此方法的分割的块可能大于tiktoken标记器计算的块大小。
.from_tiktoken_encoder()
方法接受的参数:
encoding_name
:指定使用的tiktoken
编码名称。cl100k_base
是OpenAI
为gpt-3.5-turbo
和gpt-4
模型设计的编码方案,文本分割器会依据这个编码方案把文本转换为token
序列,再按 token 数量进行分割。model_name
:指定要使用的模型名称,进而获取对应的tiktoken
编码。如果
model_name
不为 None,会调用tiktoken.encoding_for_model(model_name)
方法,依据传入的模型名称获取对应的编码。不同的模型可能使用不同的编码方案,使用encoding_for_model
能确保获取到正确的编码。若model_name
为 None,则使 编码。模型与
tiktoken
编码映射:见 tiktoken 包的 model.py文件的常量MODEL_TO_ENCODING
。chunk_size
:设置每个分割后的文本块包含的最大 token 数量。这里表示每个文本块最多包含 100 个 token。chunk_overlap
:设置相邻文本块之间重叠的token
数量。示例里设为 0,意味着相邻文本块之间没有重叠。
RecursiveCharacterTextSplitter
如果要强制硬约束 token
限制的数量,可以使用 RecursiveCharacterTextSplitter.from_tiktoken_encoder
,如果每个分割的块较大时,则将其递归分割,直到满足限制。
CharacterTextSplitter
和RecursiveCharacterTextSplitter
的from_tiktoken_encoder()
方法都是继承自TextSplitter
。
1 | from langchain_text_splitters import RecursiveCharacterTextSplitter |
API指南:RecursiveCharacterTextSplitter
TokenTextSplitter
还可以使用TokenTextSplitter
分割器,它直接与tiktoken
一起工作,并确保每次拆分都小于设置的块大小。
1 | from langchain_text_splitters import TokenTextSplitter |
执行结果:
1 | 2024年是实现“十四五 |
API指南:TokenTextSplitter
某些书面语言(如中文、日文)的字符会编码为2个或更多分词(token
)。直接使用TokenTextSplitter
可能导致字符的分词被拆分到不同文本块中,从而产生无效的Unicode
字符。建议改用RecursiveCharacterTextSplitter.from_tiktoken_encoder
或CharacterTextSplitter.from_tiktoken_encoder
方法,以确保每个文本块包含合法的Unicode字符串。
spaCy分割器
注:spaCy 用于高级自然语言处理的开源软件库,是 langchain 库中的一个文本分割工具,借助 spaCy
库可以根据语言规则对文本进行分割,用Python和Cython编程语言编写的。
LangChain基于spaCy标记器实现了分割器。
- 文本如何分割:通过
spaCy
标记器。 - 如何测量块大小:按字符数。
安装依赖:
1 | %pip install --upgrade --quiet spacy |
主要参数:
pipeline
:指定要使用的spaCy
语言模型管道名称,默认值为"en_core_web_sm"
。不同语言模型支持不同语言,例如"zh_core_web_sm"
用于中文。chunk_size
:每个文本块的最大字符数,默认值为500
。chunk_overlap
:相邻文本块之间重叠的字符数,默认值为200
。该值必须小于chunk_size
。length_function
:用于计算文本长度的函数,默认使用len
函数。
pipeline
语言模型库的安装:
1 | # 默认使用英文语言模型 en_core_web_sm |
使用示例:
1 | from langchain_text_splitters import SpacyTextSplitter |
API指南:SpacyTextSplitter
SentenceTransformers
SentenceTransformersTokenTextSplitter 是专为sentence-transformers
设计的文本分词和分割工具。其默认行为是将文本分割成适合目标模型分词窗口大小的文本块。
SentenceTransformersTokenTextSplitter
通过对齐模型的分词机制,使分割后的文本块最大程度保留原始语义信息,为后续的嵌入、检索、生成等任务提供高质量输入基础。
模型感知的分割(核心优势):
- 与目标模型对齐:使用与 Sentence Transformer 模型完全相同的分词器,确保:
- 分割边界与模型预训练时的语义单元一致
- 避免在语义关键位置(如词根、词组中间)切割
- 规避模型截断风险:精确计算token数量,确保每个chunk不超过模型最大长度
✅ 效果:提升下游任务(如嵌入生成)质量10-25%(Hugging Face 基准测试)
若需根据 sentence-transformers
分词器进行文本分割并控制分词数量,安装依赖库。
1 | pip install sentence-transformers |
实例化参数
实例化 SentenceTransformersTokenTextSplitter
,可选的配置项包括:
model_name
:指定预训练模型的名称或本地路径,其核心目的是确定模型的架构、预训练权重及训练目标,从而为后续的文本编码或微调任务提供基础模型支持。默认值为
sentence-transformers/all-mpnet-base-v2
。chunk_size
:分割的每个文本块的理想 token 数量,分割器会尽量创建接近该大小的块。实际分割可能略低于或高于此值(为保持语义完整性),默认值为512
。chunk_overlap
:相邻文本块之间重叠的 token 数量,默认值为0
。tokens_per_chunk
:分割的每个文本块的绝对最大token数量,硬性限制。此参数具有最高优先级,如果设置,会覆盖chunk_size的限制,可能导致句子被强行截断(影响语议完整性),适用于严格控制 token 预算的特殊场景。建议:优先使用
chunk_size
作为主要控制参数,仅在需要严格限制token数量时才使用tokens_per_chunk
,并始终考虑模型的实际token限制。encoding_name
:指定使用的编码名称,若未指定,会根据model_name
自动选择合适的编码。disallowed_special
:不允许出现在 token 中的特殊字符集合,默认值为DENY_LIST
,即不允许任何特殊字符。allowed_special
:允许出现在 token 中的特殊字符集合,默认值为set()
,即不允许任何特殊字符。
model_name说明
model_name
参数本质是模型架构的标识符,但通过 Hugging Face 的 API 设计,它间接关联了对应的分词器。开发者无需单独指定分词器名称,只需确保 model_name
正确,即可自动完成模型与分词器的协同加载。
在 SentenceTransformer
或 Hugging Face 的 transformers
库中,model_name
参数同时关联模型架构和分词器。
- 模型标识:
model_name
主要用于指定预训练模型的架构和权重(如 BERT、MPNet 等),通常包含分词器类型信息,例如bert-base-uncased
→ BERT 模型 + 对应的分词器(WordPiece)gpt2
→ GPT-2 模型 + 对应的分词器(BPE)
- 分词器绑定:模型名称隐含了分词器的类型,通过
AutoTokenizer.from_pretrained(model_name)
自动匹配与模型预训练时相同的分词规则。
使用示例一
1 | # 从 langchain_text_splitters 模块导入 SentenceTransformersTokenTextSplitter 类 |
使用示例二
1 | from langchain.text_splitter import SentenceTransformersTokenTextSplitter |
API指南:SentenceTransformersTokenTextSplitter
SentenceTransformers
库提供了许多支持中文分词的预训练模型,下面列举一些常用的模型名称,可以将这些名称赋值给 model_name
使用。
模型分词器
多语言通用模型
sentence-transformers/paraphrase-multilingual-mpnet-base-v2
:在多语言语义相似度任务上表现出色,可用于中文文本的语义理解和对比。sentence-transformers/paraphrase-multilingual-MiniLM-L12-v2
:支持多语言的跨语言语义匹配模型。相比前者模型更小、推理速度更快,在保证一定性能的同时能节省资源。sentence-transformers/all-mpnet-base-v2
:性能优秀的多语言模型,能生成高质量的句子嵌入。distiluse-base-multilingual-cased-v2
:轻量级多语言模型,适合对速度有要求的场景。
中文专用模型
这些模型专门针对中文进行了优化,在中文相关任务上效果更佳。
shibing624/text2vec-base-chinese
:由中文 NLP 领域专家训练,在中文文本向量化、相似度计算等任务中表现良好。GanymedeNil/text2vec-large-chinese
:模型规模较大,有更强大的语义表示能力,适合对精度要求较高的中文任务。
使用示例:
1 | from langchain_text_splitters import SentenceTransformersTokenTextSplitter |
执行结果:
1 | 多语言模型分割结果: ['这是一段中文测试文本。'] |
英文专用模型
专门为英文文本设计,在英文任务上通常有更好的表现。
all-MiniLM-L6-v2
:轻量级英文模型,速度快,适合资源受限的环境。all-roberta-large-v1
:较大的英文模型,性能强劲,但推理速度相对较慢。
特定任务模型
针对特定任务进行优化的模型。
nli-mpnet-base-v2
:在自然语言推理任务上表现出色。quora-distilbert-multilingual
:针对问答任务优化的多语言模型。multi-qa-mpnet-base-dot-v1
:专门用于语义搜索和问答任务。常用于构建知识库问答系统,比如结合向量数据库进行检索增强生成。主要面向英语,但通过微调可扩展至其他语言场景(如中文问答系统)。distilbert-base-nli-stsb-mean-tokens
:适用于微调自定义任务。基于 STS 预训练,微调后相似度计算更准。
NLTK
自然语言工具包(通常简称为NLTK)是一套基于Python编程语言编写的库和程序套件,用于英语的符号化与统计化自然语言处理(NLP)。
与其仅依据**"\n\n"
**进行切分,我们可以使用NLTK
的分词器进行文本切分。
- 文本切分方式:通过
NLTK
分词器(tokenizer
)。 - 区块大小计量方式:依据字符数量。
NLTKTextSplitter
NLTKTextSplitter 是基于自然语言处理库 NLTK 实现的结构化文本分割工具,专为处理英文文本设计。其核心价值在于替代朴素的分隔符切割(如"\n\n"
),通过语言学规则实现符合语义逻辑的文本分块。
NLTKTextSplitter
在保留文本语义结构与控制信息密度之间取得平衡,成为处理英文文档预处理的标准工具之一。开发者可根据实际需求在字符级精度与计算效率间灵活调整参数。
使用示例
安装依赖:
1 | pip install nltk |
使用示例:
1 | # 从 langchain_text_splitters 库中导入 NLTKTextSplitter 类 |
API指南:NLTKTextSplitter
Hugging Face分词器
Hugging Face平台提供多种分词器。
我们采用Hugging Face的GPT2TokenizerFast
分词器来统计文本的token数量。
- 文本切分方式:按传入字符切分
- 区块大小计量方式:依据Hugging Face分词器计算的token数量
使用示例:
1 | # 从 transformers 库中导入 GPT2 快速分词器类 |
API指南:CharacterTextSplitter
LangChain:文本切割器如何根据tokens拆分文本
http://blog.gxitsky.com/2025/06/02/AI-LangChain-016-TextSpliter-How/