← 返回笔记列表
AI 技术与原理 第 7 / 28 篇

AI 原理学习笔记(七):文字怎样变成 Token、Embedding 与向量

查看“AI 技术与原理”专题目录(7/28)
本文目录 9 个小节

返回系列导读 · 先修:向量和矩阵

1. 文字为什么不能直接交给矩阵计算

神经网络接收数字。“猫”是一个符号,电脑保存它的字符编码,不等于模型已经知道它与“狗”有什么关系。

把文本送入模型,通常先经历:

文本 → 分词器 Tokenizer → Token ID 序列
     → Embedding 查表 → 一串向量 → 神经网络

这里每一步负责不同工作。分词器决定如何切分与编号,Embedding 把编号变成可学习的数字表示。

2. Token 不等于汉字,也不等于一个词

Token 是分词器使用的基本单位,可以是完整单词、子词、标点、字节片段或特殊标记。具体切法依赖模型的词表和算法。

为了理解,可以想象一个教学词表里有“机器”“学习”“很”“有趣”。“机器学习很有趣”被切成四个 Token。但真实模型可能使用不同切法,不能把这个例子当作某个实际分词器的输出。

词表 vocabulary 是 Token 到编号的映射。编号只标识条目,没有自然大小:ID=100 并不比 ID=50“意思大一倍”。

同一句话换模型,Token 数可能变化。上下文限制和 API 计费都要按具体 Tokenizer 算,不能把汉字数乘一个永久固定系数。

3. BPE 为什么能压缩词表

如果把所有完整词都存进词表,稀有词和新词会很多;如果全按字符或字节处理,序列又可能很长。

BPE 的基本思路是从较小单元开始,反复合并经常一起出现的相邻单元。例如训练语料中“学”“习”经常相邻,可能被合成一个更长单元。

这是对语料统计的利用,不是先理解语法再划词。不同算法还可能使用不同的概率模型或归并规则;看见“子词”并不意味着所有分词器都完全按照同一种 BPE 实现。

特殊 Token 可能代表句首、结束、角色边界或填充。聊天模板如何组织角色,同样影响最终输入序列。

进一步看词表与 BPE。

4. Embedding 本质上是一张参数表

设词表有 VV 个 Token,每个向量长 DD,Embedding 参数矩阵为:

E∈RV×DE\in\mathbb R^{V\times D}

输入 Token ID 为 ii,就取第 ii 行 EiE_i。这一步是查表,不是拿 ID 的数值去算语义。

例如教学词表只有 5 项,每项 3 维:

ID=0 → [ 0.1,  0.2,  0.3]
ID=1 → [-0.4,  0.5,  0.0]
...

输入 shape 为 [B,T][B,T],查表后变成 [B,T,D][B,T,D]。BB 是序列数,TT 是每条序列 Token 数,DD 是表示维度。

向量一开始可以随机初始化,训练后才逐渐形成对任务有用的关系。第 17 维通常不能直接解释为“快乐值”;模型的信息常分布在许多维度的组合中。

5. 静态词向量与上下文表示

Word2Vec 一类方法让经常出现在相似上下文的词形成某些相似关系,常见教学形式是用周围词预测中心词,或用中心词预测周围词。

“银行”在不同句子里含义可能变化。一个固定词向量无法充分表达这些上下文差别。

在 Transformer 中,同一个 Token 的初始 Embedding 相同,但经过注意力等层后,表示会结合上下文。这个上下文隐状态与最初的查表向量不是同一概念。

另一个常见对象是句向量或文档向量:为整句话或整个文本块生成一个向量,用于检索。它需要合适的训练目标与聚合方式,不能随便把任意 LLM 的最后一层平均一下,就假定具有理想检索效果。

6. 余弦相似度在比较什么

向量点积会受到长度影响。余弦相似度除以两个向量的长度,更关注方向:

cos⁡(a,b)=a⊤b∥a∥2∥b∥2\cos(a,b)=\frac{a^\top b}{\|a\|_2\|b\|_2}

令 a=[1,0]a=[1,0],b=[2,0]b=[2,0],两者方向相同,余弦为 1;令 c=[0,1]c=[0,1],与 aa 垂直,余弦为 0。

在合适训练的语义向量空间里,方向相近常表示语义相关。但“词义相反”不一定余弦为负,因为反义词可能出现在非常相似的语境里。

余弦 0.8 也不表示“有 80% 概率相关”。阈值需要用本任务的标注样本校准,换模型后不能沿用旧阈值。

from math import sqrt

def cosine(a, b):
    dot = sum(x * y for x, y in zip(a, b))
    norm_a = sqrt(sum(x * x for x in a))
    norm_b = sqrt(sum(y * y for y in b))
    if len(a) != len(b) or norm_a == 0 or norm_b == 0:
        raise ValueError("维度要一致,且不能是零向量")
    return dot / (norm_a * norm_b)

print(cosine([1, 0], [2, 0]))  # 1.0
print(cosine([1, 0], [0, 1]))  # 0.0

代码只是在演示数学运算,没有把自然语言变成语义向量。真正的文本向量需要经过训练好的 Embedding 模型计算。

7. 向量检索为什么能处理不同说法

文档写“职工年度带薪休假”,用户问“年假有几天”。关键词不完全一致,但语义向量模型若训练得当,可能把它们放到较近的位置。

系统先为所有文档块算向量,再为问题算向量,找相似项。数据很大时,常用近似最近邻索引,以少量召回损失换取速度。

关键约束:

  • 文档与问题要使用兼容的表示空间,遵守模型要求的输入格式。
  • 换 Embedding 模型后,一般需要重新计算文档向量与索引。
  • 高相似度不保证包含答案;权限、时间、版本仍要检查。
  • 长文向量可能稀释局部细节,所以通常还需要分块与重排。

复习卡片与自测

  • Tokenizer 切分并编号,Embedding 把编号映射到向量。
  • Token ID 没有语义大小。
  • 初始 Embedding、上下文隐状态、检索句向量要分清。
  • 相似度是分数,不自动等于正确概率。

1. 两个模型都输出 768 维向量,可以混在同一个库里比较吗?

参考答案不能只看维度。它们的坐标空间和训练目标可能不同,需要确定兼容性,通常应统一模型和处理规则。

2. 为什么“128K 上下文等于 128K 汉字”不成立?

参考答案窗口按 Token 计数,汉字与 Token 的对应取决于分词器、具体文本和特殊标记。

3. 同一个词在不同句子的最终表示是否一样?

参考答案初始查表向量可能一样,但经过读取上下文的网络层后,隐表示通常不同。

原文定位

依据:原资料 3.8、4.2、6.2。补充:Token 编码。

继续学习本专题