05. 位置编码为什么重要?绝对位置编码和相对位置编码有什么区别?

整理位置编码的必要性,以及绝对/相对位置编码的区别。

简单回答

Transformer 的 Self-Attention 本身是 permutation invariant(置换不变)的——打乱输入顺序,输出不变(只是跟着打乱)。但语言的含义高度依赖词序,所以必须通过位置编码注入位置信息。绝对位置编码给每个位置一个固定表示("我在第几个位置"),相对位置编码关注的是两个 token 之间的距离("我们离多远")。后者更符合语言的局部性和平移不变性,更利于长度泛化。

详细解释

为什么 Attention 是 Permutation Invariant?

Self-Attention 的计算是 。如果我们打乱输入 token 的顺序,Q、K、V 的行顺序跟着变,但 的值(每对 token 之间的点积)不变,只是矩阵行列跟着置换了。最终结果就是输出也跟着置换,但每个 token 的表示不变——模型根本不知道谁在前谁在后。

这对语言建模是致命的问题。"我吃饭"和"饭吃我"语义完全不同,模型必须知道词序。所以需要位置编码来打破这个置换不变性。

绝对位置编码

核心思想:给每个位置 t 分配一个位置向量 ,通常直接加到 token embedding 上:

Sinusoidal 位置编码(原始 Transformer):用不同频率的正弦/余弦函数生成位置向量,不需要学习参数。每个维度用不同的频率:

设计初衷是让模型可以通过线性变换从 推出 ,理论上可以编码相对位置。但实践中效果一般,因为这个线性关系在经过多层 Attention 后被稀释了。

Learned 位置编码(GPT 系列):每个位置有一个可学习的向量(和 token embedding 类似),作为参数训练。简单有效,但有致命限制——训练多长的序列就只能处理多长,见不到的位置完全没有表示。

绝对位置编码的通病:它编码的是"我在第几个位置"这个绝对信息。但在语言中,往往更重要的是"两个 token 之间的距离",而不是"某个 token 在绝对第几个位置"。一段文本放在 prompt 开头和放在中间,内部的语义关系不应该变化,但绝对位置编码会给出完全不同的表示。

相对位置编码

核心思想:不编码绝对位置,而是编码两个 token 之间的距离

T5 的相对位置 bias:在 attention score 上加一个只依赖 的可学习 bias,不改变 Q、K 本身。距离远的 token 对通常有一个负的 bias(降低注意力),远处做 bucket 化处理,用 log 分桶把远距离压缩(因为"差 50 个 token"和"差 51 个 token"没啥区别)。

ALiBi(Attention with Linear Biases):更简单,直接在 attention score 上减去一个与距离成正比的线性惩罚:。m 是每个 head 不同的斜率,不需要学习。ALiBi 的优势是在训练长度之外有比较好的泛化能力,实现也极简。

RoPE(Rotary Position Embedding):前面第 6 题已经详细讲过。它用绝对位置编码的形式实现了相对位置编码的效果——每个 token 的 Q、K 独立做旋转(绝对),但点积结果只取决于距离差(相对)。是目前最主流的方案。

各方案的对比总结

绝对位置编码(sinusoidal、learned)理解简单、实现容易,但长度泛化差,已经被主流大模型抛弃。T5 bias 和 ALiBi 是显式的相对位置编码,通过修改 attention score 来引入位置信息,实现清晰但各有局限。RoPE 是隐式的相对位置编码,通过旋转 Q、K 来编码位置,不修改 attention 结构,兼容 KV Cache,长度外推基础好,是当前的事实标准。

面试时可以这样答

位置编码的必要性来自一个核心事实:Self-Attention 是 permutation invariant 的,打乱输入顺序对 attention 计算没有影响。但语言是有序的,"我吃饭"和"饭吃我"意思完全不同,所以必须注入位置信息。

绝对位置编码给每个位置一个固定表示,典型的有 sinusoidal 和 learned。它的问题是编码的是"我在第几个位置",长度泛化差,而且同一段文本放在不同位置会有不同的表示,不太合理。

相对位置编码关注的是 token 之间的距离。T5 用的是在 attention score 上加 bias,ALiBi 用线性惩罚,RoPE 用旋转。其中 RoPE 是目前最主流的,它用绝对编码的形式实现了相对编码的效果——每个 token 独立做旋转,但点积结果只依赖距离差。而且它兼容 KV Cache,配合位置插值方法还能做长度外推。

现在主流大模型基本都用 RoPE。ALiBi 也有一些模型在用,但整体上 RoPE 已经是事实标准了。

常见追问

  1. RoPE 如何做长度外推?NTK-aware scaling 和 YaRN 的区别是什么?
  2. 如果一个模型训练时只见过 4K 长度的序列,直接推理 32K 会发生什么?
  3. 位置编码加在 embedding 上(加法)和加在 attention score 上(bias)有什么本质区别?