大型语言模型 (LLM) 通常被视为黑盒,但其基础在于一个出奇简单的过程: 分词 (tokenization) 。在模型能够理解“人工智能”之前,必须将文本分解成更小的块,即 Token (词元) 。多年来,行业标准一直是字节对编码 (BPE) ,这是一种可靠的算法,可将频繁出现的字符合并为子词。

然而,可靠并不总是意味着高效。标准 BPE 存在囤积问题。它创建并保留“中间”Token——即构建更长单词所必需但本身无用的单词片段。这些“垃圾 Token”充斥着词表,浪费了宝贵的参数,并可能降低模型性能。

在这篇文章中,我们将探讨研究人员提出的一种新方法,名为 Picky BPE 。 该算法在训练期间精简词表,识别并移除无用的 Token,为更有意义的 Token 腾出空间。我们将深入探讨其工作原理、背后的数学原理,以及为什么“挑剔一点 (being picky) ”可能是构建更安全、更高效语言模型的关键。

问题所在: 词表膨胀与“垃圾”Token

为了理解 Picky BPE,我们首先需要了解标准 BPE 的工作原理及其不足之处。BPE 从包含单个字符 (如 a, b, c) 的词表开始。它迭代地找到文本中最频繁出现的相邻 Token 对,并将它们合并成一个新的 Token。

例如,如果 “t” 和 “h” 经常一起出现,BPE 会将它们合并为 “th”。如果 “th” 和 “e” 经常一起出现,它会合并它们以创建 “the”。

问题在于 BPE 会保留它创建的每一个 Token。为了构建单词 “Kentucky” (肯塔基) ,BPE 可能首先合并 “K” 和 “entucky” (假设 “entucky” 已经形成) 。一旦 “Kentucky” 形成,Token “entucky” 仍然保留在词表中。但你上一次在句子中使用 “entucky” 这个词是什么时候?可能从来没有。它是一个 中间 Token——对合并过程有用,但在合并后就是多余的了。

下图完美地展示了这种冗余。

Figure 1: 生成 Token Kentucky 的一系列合并示例。合并前的 Token 频率显示在相应的圆圈中。在标准 BPE 算法中,entucky 也应该存储在词表中,尽管它在合并后是多余的。在这个例子中,IoS 指标有效地捕捉到了这个中间 Token,因为 IoS(entucky) >= 0.9

在固定大小的词表 (例如 32,000 个 Token) 中,每一个被垃圾 Token (如 “entucky”) 占据的位置,都是对有用 Token (如完整单词或常用前缀) 的拒绝。这导致了 词表低效

此外,这些罕见的垃圾 Token 很危险。因为它们在训练数据中出现的频率极低 (除了作为它们构建的单词的一部分) ,模型几乎学不到它们。这些 欠训练 Token (Under-trained tokens) 可能会变成 “Glitch Token” (故障 Token) ——导致模型产生幻觉或绕过安全护栏的输入,因为模型实际上不知道它们是什么意思。

解决方案: Picky BPE

研究人员提出的 Picky BPE 旨在通过在训练过程中引入“垃圾回收”机制来解决这个问题。与以往尝试在训练修剪词表的方法 (这些方法往往混乱且严重依赖启发式规则) 不同,Picky BPE 在合并发生的瞬间就决定是保留还是丢弃 Token。

指标: 自身交集 (IoS)

算法如何知道一个 Token 是垃圾?研究人员引入了一个名为 自身交集 (Intersection over Self, IoS) 的指标。

直觉很简单: 如果 Token \(x_1\) 几乎只作为更大的 Token \(x_1 + x_2\) 的一部分出现,那么 \(x_1\) 很可能只是一个不再需要的构建块。

从数学上讲,如果我们正在合并两个 Token \(x_1\) 和 \(x_2\),我们为两者计算 IoS。这是第一个 Token \(x_1\) 的公式:

Equation 1: 第一个 Token 的 IoS 计算

以及第二个 Token \(x_2\) 的公式:

Equation 2: 第二个 Token 的 IoS 计算

在这些公式中:

  • \(f_p(x_1, x_2)\) 是 对 (pair) 的频率 (它们一起出现的频率) 。
  • \(f_t(x_1)\) 是 Token \(x_1\) 在文本中任何位置出现的总频率。

结果是一个介于 0 和 1 之间的值。IoS 为 1.0 意味着 Token \(x_1\) 从不出现在文本中,除非它附着在 \(x_2\) 上。IoS 为 0.9 意味着它 90% 的时间都与 \(x_2\) 一起出现。

算法实战

Picky BPE 算法引入了一个名为 阈值 (threshold, \(\tau\)) 的超参数。这控制了算法有多“挑剔”。

  • 如果 \(\text{IoS} \ge \tau\),该 Token 将从词表中移除。
  • 较高的 \(\tau\) (如 0.9) 较为保守,只移除明显无用的 Token。
  • 较低的 \(\tau\) (如 0.6) 较为激进,会移除那些可能仍有一些独立用途的 Token。

这是训练算法的高级视图:

Algorithm 1 和 2: Picky BPE 训练和分词步骤

让我们用涉及 “would”、“could” 和 “should” 周围单词片段的具体例子来可视化这一点。

Figure 2: Picky BPE 分词示例。Token 频率显示在相应的圆圈中,并在合并时更新。Token “ould” 只有在合并进三个包含它的常用 Token 后才会被移除。相应的 IoS 值会在每次合并时显示。一旦 IoS 大于或等于阈值,本例中为 0.9,Token “ould” 就会被移除。

在上图中:

  1. 我们有 Token “ould”。
  2. 它与 “w” 合并形成 “would”。但 “ould” 也用于 “could” 和 “should”,所以它相对于 “would” 的 IoS 很低 (0.4)。它保留。
  3. 它与 “c” 合并形成 “could”。现在 “ould” 大部分已被包含,但仍用于 “should”。IoS 为 0.5。它保留。
  4. 最后,它与 “sh” 合并形成 “should”。此时,“ould” 几乎不再出现在文本的其他任何地方,除了这三个词中。其 IoS 飙升至 0.9。
  5. 由于 \(0.9 \ge \tau\) (阈值) ,“ould” 从词表中移除。

这种动态过程确保只有在整个数据集中完成了使命的 Token 才会被删除。

关键细节: 推理顺序

Picky BPE 最聪明的方面之一是它在训练后处理阅读文本 (推理) 的方式。标准的修剪方法通常会制造不一致性。如果你在训练后删除了一个 Token,你可能会意外地改变句子的切分方式,从而损害文本压缩率。

Picky BPE 严格按照时间顺序记录每一个事件——每一个 合并 (Merge) 和每一个 移除 (Remove) 。 当分词器处理新文本时,它会重放这些事件。它合并对,但如果遇到它刚刚创建的某个 Token 的“移除”事件,它就知道该 Token 在该特定序列的未来合并中不再有效。这严格遵循了训练逻辑,确保了高质量的压缩。

分析影响

那么,Picky BPE 清理了词表。但这真的对模型有帮助吗?研究人员从三个角度对此进行了分析: “故障”Token、翻译性能和文本压缩。

1. 消除“故障 Token”

欠训练 Token 是 LLM 中已知的安全风险。这些是在训练数据中出现频率极低的 Token,以至于它们的嵌入向量 (Token 含义的数学表示) 没有得到足够的更新。它们通常最终具有非常小的“L2 范数” (向量的大小) ,并可能触发不稳定行为。

研究人员比较了标准 BPE 模型和 Picky BPE 模型的 Token 嵌入。

首先,让我们看看标准 BPE (\(\tau = 1.0\),意味着不移除) 的分布。

散点图显示 Tau = 1.0 时的 Picky BPE Token。橙色点代表在 Tau = 0.8 时会被移除的 Token。

在上图 (图 a) 中,x 轴是 L2 范数 (Token 训练得有多好) ,y 轴是频率。 橙色点代表 Picky BPE 识别为垃圾的 Token。注意它们聚集在哪里: 左下角。它们是低频率且低 L2 范数的。这些正是我们想要摆脱的危险、欠训练的 Token。

现在,让我们看看当我们在阈值 \(\tau = 0.9\) 下启用 Picky BPE 时会发生什么。

等高线图显示 Tau = 0.9 时的 Picky BPE Token。粉色区域显示新添加的 Token。

在这张图 (图 b) 中, 粉色区域代表为了填补移除垃圾后留下的空间而添加的新 Token。这些新 Token 频率更高,且具有更高的 L2 范数。

结论: Picky BPE 有效地将危险、无用的 Token 替换为经常使用、训练良好的 Token。这很可能减少幻觉并提高模型安全性。

2. 文本压缩

减少词表的一个常见担忧是文本压缩率会受损。如果你移除了 Token “entucky”,你可能不得不将 “Kentucky” 表示为 ["K", "e", "n", "t", "u", "c", "k", "y"] (8 个 Token) 而不是 ["K", "entucky"] (2 个 Token) 。如果文本需要更多的 Token 来表示同一个句子,模型就会变得更慢且效率更低。

然而,因为 Picky BPE 是动态的,它不仅仅是删除;它还为新的合并腾出了空间。研究人员发现 Picky BPE 保持了出色的压缩率。

Table 11: 不同词表大小下 EN-DE 分词器的压缩率。

在上表中,压缩分数 1.000 是基准。低于 1.000 的分数表示压缩效果更好 (需要更少的 Token) 。对于英语-德语 (EN-DE) 词表,Picky BPE (\(\tau < 1.0\)) 获得的分数非常接近甚至优于基准。这比其他通常会使序列长度增加超过 10% 的词表修剪方法有显著改进。

3. 下游任务性能: 机器翻译

最后,模型的翻译效果会更好吗?研究人员在英语-德语、德语-爱沙尼亚语和乌克兰语-爱沙尼亚语翻译任务上测试了 Picky BPE。

他们发现 Picky BPE 模型的表现全面与标准 BPE 模型持平或更好 。 在困难的翻译对 (如德语-爱沙尼亚语) 中,提高的词表效率带来了更高的 COMET 分数 (一种翻译质量指标) 。

具体来说,通过移除中间垃圾,分词器能够添加更多的 词首 Token (word-initial tokens) (以单词开头的 Token,通常用通用的下划线如 _word 表示) 。

Table 17: 不同阈值下词首 Token 的总体比例

如表 17 所示,随着阈值 (\(\tau\)) 降低 (变得更严格) ,词首 Token 的百分比增加。词首 Token 通常比词中片段具有更多的语义意义,这表明词表质量正在变高。

结论

分词是现代 AI 默默无闻的主力,但它仍然充满低效。Picky BPE 算法表明,我们不需要接受“垃圾”Token 作为训练过程中必不可少的恶果。

通过利用 自身交集 (IoS) 指标,Picky BPE 提供了一种数学上合理的方法来区分有用的子词和冗余的产物。结果显而易见:

  1. 更干净的词表: 冗余 Token 被移除。
  2. 更高的效率: 释放出的槽位被有意义的、高频的 Token 填充。
  3. 提高的安全性: 导致模型不稳定的“故障 Token”在很大程度上被消除。
  4. 没有负面影响: 压缩率和翻译性能得以保持或提高。

随着语言模型的规模和成本不断增长,每一个参数都很重要。像 Picky BPE 这样的方法提供了一顿“免费的午餐”——一种仅通过对进入字典的内容更挑剔一点,就能提高模型质量和安全性的方法。