尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

PaddleSpeech N-Gram 语言模型实战:基于 KenLM 训练中文字符级与词级 LM 全流程

PaddleSpeech N-Gram 语言模型实战:基于 KenLM 训练中文字符级与词级 LM 全流程 人工智能语音音频NLP媒体生成【免费下载链接】PaddleSpeechEasy-to-use Speech Toolkit including Self-Supervised Learning model, SOTA/Streaming ASR with punctuation, Streaming TTS with text frontend, Speaker Verification System, End-to-End Speech Translation and Keyword Spotting. Won NAACL2022 Best Demo Award.项目地址https://gitcode.com/paddlepaddle/PaddleSpeech点击查看免费下载本指南以 PaddleSpeech 仓库中的 examples/other/ngram_lm 示例为主体完整讲解如何基于 KenLM 从纯文本语料训练中文字符级char与词级wordn-gram 语言模型并量化为可供加载的二进制模型。读完本文你将掌握从文本正则化、分词预处理、lmplz训练、build_binary量化到用 KenLM 的score/full_scores/perplexity接口对句子打分评测的完整链路可直接用于 ASR 解码重打分、文本纠错等场景的语言模型构建。一、示例背景语音工具链中的 n-gram 语言模型在语音识别ASR与文本纠错任务中声学模型输出的候选序列往往需要语言模型Language Model, LM提供词序先验从发音相近的多个候选中选出概率最高、最符合自然语言习惯的一句。n-gram 语言模型通过统计连续 n 个 token字符或词的共现频次来估计句子的概率具有训练快、可解释性强、可离线部署等优点是统计语言建模的经典方案。PaddleSpeech 在examples/other/ngram_lm目录下提供了完整的 n-gram 语言模型构建示例顶层 README 简要列出s0 - kenlm ngram lm一个子方案其核心实现位于 s0。该示例覆盖下载仓库预发布的中文 KenLM 模型并测试评分 API使用中文电商问答语料data/text_correct.txt训练字符级 5-gram 与词级 3-gram 语言模型将 ARPA 文本模型量化为 trie 结构的二进制模型.klm.bin。整个流程基于 KenLM 工具链lmplz训练 build_binary量化训练语料规模小、可在普通 CPU 上数分钟内完成非常适合作为语言模型构建的入门与基准实验。二、示例结构与运行入口examples/other/ngram_lm/s0目录结构如下examples/other/ngram_lm/s0/ ├── README.md ├── path.sh ├── requirements.txt ├── run.sh ├── data/ │ ├── README.md │ ├── custom_confusion.txt │ └── text_correct.txt └── local/ ├── build_zh_lm.sh ├── download_lm_zh.sh └── kenlm_score_test.py运行入口为run.shs0/README.md 给出的运行方式只有两条命令. path.sh bash run.sh其中 path.sh 负责初始化环境它将仓库根目录设为MAIN_ROOT通过realpath ${PWD}/../../../../计算把仓库根目录与utils/目录加入PATH和PYTHONPATH并设置LC_ALLC与PYTHONIOENCODINGUTF-8保证脚本中的中文文本在管道与 Python 交互时编码正确。依赖方面requirements.txt 只声明了jieba0.39用于中文分词KenLM 的 Python 绑定import kenlm需要单独安装run.sh在开头会用python3 -c import kenlm;做环境自检未安装时直接报错退出python3 -c import kenlm; || { echo kenlm package not install!; exit -1; }run.sh采用 PaddleSpeech 示例通用的stage/stop_stage分段执行模式可通过命令行参数utils/parse_options.sh解析控制执行区间例如只跑第 1 阶段可传--stage 1 --stop_stage 1。三、stage 0下载预训练中文 LM 并验证 KenLM 评分接口第 0 阶段stage -le 0做两件事下载仓库预发布的中文语言模型然后运行评分测试脚本验证 KenLM Python API 的正确性。下载逻辑封装在 download_lm_zh.sh 中目标模型为文件名zh_giga.no_cna_cmn.prune01244.klm存放路径data/lm/zh_giga.no_cna_cmn.prune01244.klmMD5 校验值29e02312deb2e59b3c8686c7966d4fe3下载工具调用仓库 utils/utility.sh 中定义的download函数下载后自动做 MD5 校验文件已存在则直接跳过该模型是从大规模中文语料Giga 规模、去除 CNA/CMN 部分训练并剪枝prune01244表示按计数剪枝阈值得到的字符级 KenLM 二进制模型约百兆量级可直接被kenlm.Model加载。评分测试脚本 kenlm_score_test.py 是一个可独立运行的自测程序用法为python local/kenlm_score_test.py data/lm/zh_giga.no_cna_cmn.prune01244.klm它通过assert验证了 KenLM Python 接口的若干关键行为构成一个微型回归测试集主要包括1.score与full_scores的粒度差异model kenlm.Model(language_model_path) sentence 盘点不怕被税的海淘网站❗️海淘向来便宜又保真 sentence_char_split .join(list(sentence)) sentence_word_split .join(jieba.lcut(sentence)) print(model.score(sentence)) # 整句 log10 概率 print(list(model.full_scores(sentence))) # 逐 token 的 (概率, n-gram 长度, 是否 OOV)score返回整句的对数概率含s与/sfull_scores则返回每个 token 对应的三元组(prob, length, oov)其中length是命中的 n-gram 阶数oov标记是否为词典外词。脚本断言了字符切分时full_scores输出个数等于“字符数 1”多出的一个来自s。2. OOV词典外词检测words [s] list(sentence) [/s] for w in words: if w not in model: print({0} is an OOV.format(w))对字符级模型脚本断言[❗, ️, ]为 OOV对词级切分断言[盘点, 不怕, 网站, ❗, ️, 海淘, 向来, 便宜, 保真, ]为 OOV——这正好说明该预训练模型是字符级模型词级切分后几乎全部词都会 OOV。3.bos/eos控制r list(model.full_scores(sentence_char_split)) # 默认带 s 和 /s n list(model.full_scores(sentence_char_split, bosFalse, eosFalse)) assert len(r) len(n) 1 assert len(n) len(sentence_char_split.split())bosFalse, eosFalse时输出数量与输入 token 数一致便于在解码器中精确控制句首句尾标记。4. 句子粒度的perplexityn model.perplexity( .join(先救挨饿的人然后治疗病人。)) n model.perplexity( .join(先就挨饿的人然后治疗病人。))脚本对“救”与“就”这类同音异形字构造 8 组递增长度的对比验证字符模型能通过困惑度区分正确/错误文本当上下文长度不足时如只给“先救挨”三个字符两者困惑度相等assert n1 n2体现了 n-gram 模型的上下文窗口特性。四、stage 1训练字符级 5-gram 语言模型第 1 阶段构建字符级中文 LM关键参数在 run.sh 中定义inputexp/text token_typechar langzh order5 prune0 1 2 4 4 a22 q8 b8 output${input}_${lang}_${token_type}_o${order}_p${prune// /_}_a${a}_q${q}_b${b}.arpa bash local/build_zh_lm.sh --order ${order} --prune ${prune} --a ${a} --q ${q} --b ${b} ${token_type} ${input} ${output}由参数拼出的输出文件名为exp/text_zh_char_o5_p0_1_2_4_4_a22_q8_b8.arpa命名规则为输入名_语种_token类型_o阶数_p剪枝_a量化a_q量化q_b量化b一眼即可看出模型配置。在此之前run.sh会先把语料复制进工作目录mkdir -p exp cp data/text_correct.txt exp/text语料 text_correct.txt 是中文电商购物问答文本来自开源纠错项目 pycorrector 的测试语料内容口语化、含大量错别字与商品咨询句例如“少先队员因该为老人让坐”“祛痘印可以吗有效果吗”等恰好适合作为语言模型与纠错任务的评测语料同目录的custom_confusion.txt为自定义混淆字词表相关说明见 data/README.md。字符级 5-gram 采用prune0 1 2 4 4即对 2-gram 到 5-gram 分别按计数 1、2、4、4 进行剪枝显著压缩模型体积a22 q8 b8为build_binary的量化参数。五、stage 2训练词级 3-gram 语言模型第 2 阶段构建词级中文 LM与字符级差异主要在token_type、order与pruneinputexp/text token_typeword langzh order3 prune0 0 0 a22 q8 b8 output${input}_${lang}_${token_type}_o${order}_p${prune// /_}_a${a}_q${q}_b${b}.arpa bash local/build_zh_lm.sh --order ${order} --prune ${prune} --a ${a} --q ${q} --b ${b} ${token_type} ${input} ${output}词级模型阶数取 3、不剪枝prune0 0 0输出为exp/text_zh_word_o3_p0_0_0_a22_q8_b8.arpa。由于词表规模远大于字符集词级 n-gram 计数矩阵更大3 阶已是口语电商语料仅 220 行的合理选择避免高阶统计过于稀疏。六、文本预处理zh_tn.py 正则化与分词无论是字符级还是词级训练前都要经过 build_zh_lm.sh 的预处理阶段python3 ${MAIN_ROOT}/utils/zh_tn.py --token_type ${type} ${text} ${text}.${type}.tn该命令调用仓库根目录下的 utils/zh_tn.py 完成“文本正则化text normalization, TN 分词”两步--token_type取char或word输出分别写入exp/text.char.tn与exp/text.word.tn。zh_tn.py实现了一套完整的中文文本正则化规则核心包括数字转中文阿拉伯数字改写为汉字读法如“13斤”→“十三斤”示例输出exp/text.char.tn中“我家宝宝十三斤用多大码的”可见全角/半角归一化内置QJ2BJ全角转半角映射表全角空格、标点转半角标点与特殊符号处理基于 zhon 汉字字符集定义的中文标点停用/非停用集合进行规整量词、货币、时间等规则内置CURRENCY_NAMES、COM_QUANTIFIERS等常量配合正则匹配做口语数字的展开儿化音白名单通过ER_WHITELIST保护“儿童、儿女”等不应被儿化拆分的词。char模式下输出为空格分隔的字符序列word模式下由jieba完成分词。以语料前几行为例两个预处理产物的对比如下 exp/text 少先队员因该为老人让坐 祛痘印可以吗有效果吗 不知这款牛奶口感怎样 小孩子喝行吗 exp/text.char.tn 少 先 队 员 因 该 为 老 人 让 坐 祛 痘 印 可 以 吗 有 效 果 吗 不 知 这 款 牛 奶 口 感 怎 样 小 孩 子 喝 行 吗 exp/text.word.tn 少先队员 因该 为 老人 让 坐 祛痘 印 可以 吗 有 效果 吗 不知 这 款 牛奶 口感 怎样 小孩子 喝行 吗可见词级切分后保留词语整体作为统计单元如“少先队员”“牛奶”而字符级切分则彻底打散到单字两者适合不同粒度的建模需求。七、训练与量化ngram_train.sh 详解预处理完成后的训练阶段同样封装在 build_zh_lm.sh 中最终调用仓库通用脚本 utils/ngram_train.shlmplz -o ${order} -S ${mem} --prune ${prune} ${text} ${arpa} build_binary -a ${a} -q ${q} -b ${b} trie ${arpa} ${lmbin}第一步lmplz训练 ARPA 模型。lmplz是 KenLM 的计数估计estimation工具关键参数如下参数默认值ngram_train.sh说明-o/--order5n-gram 最大阶数字符级示例取 5词级取 3-S/--memory80%训练内存上限可用百分比或绝对大小如50%、2G超过则自动落盘排序--prune0剪枝计数阈值空格分隔、每阶一个值0表示不剪枝字符级示例的prune0 1 2 4 4含义为1-gram 不剪阈值 02-gram 计数小于 1 的丢弃3-gram 小于 2 的丢弃4-gram/5-gram 小于 4 的丢弃。剪枝可大幅压缩模型代价是长上下文的覆盖度下降。第二步build_binary量化为 trie 模型。ARPA 是纯文本格式加载慢、内存大因此用build_binary编译为紧凑的二进制模型.klm.bin参数默认值说明-a22trie 数组的 bit 位宽影响最大概率精度官方建议 22–25-q8概率/回退权重量化 bit 数8 即 8-bit 量化-b8回退权重backoff单独量化 bit 数trie—数据结构类型build_binary支持的 probing / trie / quantized trie 之一示例中a22 q8 b8是 KenLM 官方推荐的“量化 trie”组合在精度损失极小通常 1% 困惑度的前提下显著减小内存占用适合服务端部署。训练完成后run.sh中mkdir -p exp之后的产物与 README 给出的目录树一致exp/ |-- text |-- text.char.tn |-- text.word.tn |-- text_zh_char_o5_p0_1_2_4_4_a22_q8_b8.arpa |-- text_zh_char_o5_p0_1_2_4_4_a22_q8_b8.arpa.klm.bin |-- text_zh_word_o3_p0_0_0_a22_q8_b8.arpa -- text_zh_word_o3_p0_0_0_a22_q8_b8.arpa.klm.binREADME 同时给出了全部产出物的 MD5 校验值便于复现时核对文件完整性3ae083627b9b6cef1a82d574d8483f97 exp/text d97da252d2a63a662af22f98af30cb8c exp/text.char.tn c18b03005bd094dbfd9b46442be361fd exp/text.word.tn 73dbf50097896eda33985e11e1ba9a3a exp/text_zh_char_o5_p0_1_2_4_4_a22_q8_b8.arpa 01334e2044c474b99c4f2ffbed790626 exp/text_zh_char_o5_p0_1_2_4_4_a22_q8_b8.arpa.klm.bin 36a42de548045b54662411ae7982c77f exp/text_zh_word_o3_p0_0_0_a22_q8_b8.arpa 332422803ffd73dd7ffd16cd2b0abcd5 exp/text_zh_word_o3_p0_0_0_a22_q8_b8.arpa.klm.bin八、读懂 ARPA 模型文件ARPA 文件是语言模型的标准文本交换格式README 展示了两个模型的头部统计信息 exp/text_zh_char_o5_p0_1_2_4_4_a22_q8_b8.arpa \data\ ngram 1587 ngram 2395 ngram 3100 ngram 42 ngram 50 \1-grams: -3.272324 unk 0 0 s -0.36706257 exp/text_zh_word_o3_p0_0_0_a22_q8_b8.arpa \data\ ngram 1689 ngram 21398 ngram 31506 \1-grams: -3.1755018 unk 0 0 s -0.23069073 -1.2318869 /s 0 -3.067262 少先队员 -0.051341705解读要点\data\下的ngram kN统计各阶 n-gram 条目数。字符级 5-gram 因剪枝与语料较小4-gram 仅 2 条、5-gram 为 0高阶层数被剪枝完全去除词级 3-gram 不剪枝1-gram 689、2-gram 1398、3-gram 1506统计随阶数增长。\1-grams:每行三个字段log10 概率、token、回退权重backoff。unk表示未知词兜底概率s句首概率恒为 0/s句尾无回退权重。词级模型中“少先队员”以整词形式出现在 1-gram 中与预处理阶段text.word.tn的分词结果一一对应。九、产出模型的加载与复用训练出的.klm.bin二进制模型可直接被 KenLM Python 绑定加载加载与评分方式与第 3 阶段测试脚本完全一致import kenlm model kenlm.Model(exp/text_zh_char_o5_p0_1_2_4_4_a22_q8_b8.arpa.klm.bin) # 整句打分log10 概率 model.score(少 先 队 员 因 该 为 老 人 让 坐) # 逐 token 打分返回 (prob, n-gram 命中长度, 是否 OOV) for prob, length, oov in model.full_scores(少 先 队 员 因 该): print(prob, length, oov) # 句子困惑度 model.perplexity(少 先 队 员 因 该 为 老 人 让 坐)典型应用场景包括ASR 解码重打分将声学模型输出的多个候选句代入 LM 计算语言分与声学分加权融合后选出最优句文本纠错/拼写检查对候选修正句计算困惑度或整句概率选择语言模型得分更高者对应kenlm_score_test.py中“救/就”的对比思路语料质量筛选批量计算语料困惑度剔除明显不合语法的句子。此外从仓库整体结构看PaddleSpeech 的 C 运行时runtime在构建层面集成了 KenLM见 runtime/cmake/kenlm.cmake本示例产出的 ARPA / 二进制模型可作为此类解码服务的外部语言模型资源而 utils/zh_tn.py 与 utils/ngram_train.sh 均为仓库通用脚本可脱离该示例在任意语料上直接复用构建属于你自己的领域语言模型。十、小结一键复现与扩展路径完整复现本示例只需三步# 1. 安装依赖jieba 与 kenlm python 包 pip install jieba kenlm # 2. 进入示例目录初始化环境 cd examples/other/ngram_lm/s0 . path.sh # 3. 一键运行下载预训练 LM、测试 API、训练字符级与词级 LM bash run.sh若只想执行其中某个阶段可利用--stage/--stop_stage控制例如bash run.sh --stage 1 --stop_stage 1仅训练字符级模型。扩展时将data/text_correct.txt替换为你自己的领域语料保持每行一句的格式调整order、prune、a/q/b等参数即可在数分钟内得到领域定制的 ARPA 与量化二进制语言模型接入后续 ASR 重打分或纠错流程。赞分享人工智能语音音频NLP媒体生成【免费下载链接】PaddleSpeechEasy-to-use Speech Toolkit including Self-Supervised Learning model, SOTA/Streaming ASR with punctuation, Streaming TTS with text frontend, Speaker Verification System, End-to-End Speech Translation and Keyword Spotting. Won NAACL2022 Best Demo Award.项目地址https://gitcode.com/paddlepaddle/PaddleSpeech点击查看免费下载相关推荐终极演示文稿制作神器 Backslide用 Markdown 快速创建专业 HTML 演示终极演示文稿制作神器 Backslide用 Markdown 快速创建专业 HTML 演示 Backslide 是一款强大的 CLI 工具能够帮助用户使用人工智能语音音频NLP媒体生成3000戴森球计划工厂蓝图从新手到星际霸主的自动化革命3000戴森球计划工厂蓝图从新手到星际霸主的自动化革命 你是否曾在《戴森球计划》中看着混乱的传送带网络感到绝望当资源流动不畅、生产线停滞不前时那种挫败感人工智能语音音频aos-ce capsule-openaiOpenAI 原生 LLM 驱动胶囊实战——Responses API、模型发现与 SSE 流解析aos ce capsule openaiOpenAI 原生 LLM 驱动胶囊实战——Responses API、模型发现与 SSE 流解析 在 Unicit上一篇ZFS-inplace-rebalancing终极ZFS存储池数据重平衡解决方案下一篇用 CLAUDE.md 给 AI 编程助手立规矩Context Engineering 项目规则文件实战指南创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表