You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何让HuggingFace Tokenizer识别换行符?自定义语言模型需求

解决WordPiece Tokenizer保留换行符的问题

问题根源是默认的BertPreTokenizer会将所有空白字符(包括换行符\n)统一替换为空格,导致编码解码后换行丢失。要保留换行以生成结构化段落,需从预处理、训练、解码三个环节调整:

1. 添加换行专用特殊token

将<NL>作为表示换行的特殊token加入训练词汇表,让Tokenizer能识别并保留换行信息。

2. 修改预处理器

在预分词阶段,先将文本中的\n替换为<NL>,再使用BertPreTokenizer进行常规分词,确保<NL>被当作独立token处理。

3. 调整解码器

解码时将<NL>还原回\n,恢复原始换行格式。

修改后的完整代码

from tokenizers import Tokenizer
from tokenizers.models import WordPiece
from tokenizers import normalizers
from tokenizers.normalizers import NFD, StripAccents
from tokenizers.pre_tokenizers import Sequence, Replace, BertPreTokenizer
from tokenizers.processors import TemplateProcessing
from tokenizers.trainers import WordPieceTrainer
from tokenizers.decoders import Sequence as DecoderSequence, Replace as DecoderReplace, WordPiece

# 初始化WordPiece Tokenizer
bert_tokenizer = Tokenizer(WordPiece(unk_token="[UNK]"))

# 保持原有的归一化配置
bert_tokenizer.normalizer = normalizers.Sequence([NFD(), StripAccents()])

# 自定义预处理器:先替换换行为<NL>,再执行Bert预分词
bert_tokenizer.pre_tokenizer = Sequence([
    Replace("\n", "<NL>"),
    BertPreTokenizer()
])

# 保持原有的后处理器配置
bert_tokenizer.post_processor = TemplateProcessing(
    single="[CLS] $A [SEP]",
    pair="[CLS] $A [SEP] $B:1 [SEP]:1",
    special_tokens=[
        ("[CLS]", 1),
        ("[SEP]", 2),
    ],
)

# 训练器添加<NL>特殊token
trainer = WordPieceTrainer(special_tokens=["[UNK]", "[CLS]", "[SEP]", "[PAD]", "[MASK]", "<NL>"])
file = 'input.txt'
bert_tokenizer.train([file], trainer)

# 自定义解码器:先WordPiece解码,再将<NL>还原为换行
bert_tokenizer.decoder = DecoderSequence([
    WordPiece(),
    DecoderReplace("<NL>", "\n")
])

# 测试编码解码
output = bert_tokenizer.encode("This is the first line.\nThis is the second line.")
print(bert_tokenizer.decode(output.ids))

关键说明

  • 预处理器的Replace步骤确保换行符被转换为可被Tokenizer识别的特殊token<NL>,避免被当作普通空格处理。
  • 训练时加入<NL>到特殊token列表,确保该token被纳入词汇表,不会被标记为[UNK]。
  • 解码器的Replace步骤将<NL>还原为原始换行符,保证输出文本的结构化格式。

额外注意事项

  • 训练数据input.txt中的换行符也会被预处理器转换为<NL>,Tokenizer会在训练过程中学习该token的用法,适配自定义语言模型需求。
  • 若不想用额外特殊标记,也可尝试直接将\n加入特殊token列表,但需调整预分词逻辑避免其被替换为空格,这种方式稳定性不如<NL>方案。

内容的提问来源于stack exchange,提问作者Alex Reed

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.18 00:23:08