从0训练LLM · 现代大模型体系 实验 实验 ≈ 30 分钟 页内实验 ×2
C3 注意力:一个 Token 怎么从别的 Token 那里取信息 实验课

我们自己训练的模型,真的在这样分配注意力吗?

实验课:在我们自己的模型里看注意力
前面十课的向量是手工构造的。这一课换成真的:我们从 0 训练的小模型在几句话上逐层逐头的真实注意力权重,每个头的模式分数,以及第一个 token 的平均注意力。再对照浏览器里跑的真 GPT-2。结论全部由数据现算,页面不预设答案。

本课一问:我们自己训练的模型,真的在这样分配注意力吗?

这一课不讲新机制,只看真实数据。先不碰:为什么这个模型的某个头会长成这样(可解释性研究的范畴,这里只做观察)。

从已有出发

从已有出发 · 累计数据流 点已学环节看形状与参数
解码层

前十课的每一个数都能手算,因为向量是我们手工构造的。可真模型里的 WQ、WK、WV 是训练出来的,没有人知道它们会长成什么样。这一课用的是 04-实践项目/ 里我们自己从 0 训练的小模型:在几句话上各跑一次前向,把每一层每个头的 softmax 权重原样导出(导出格式见 C3 设计卡「项目实验数据约定」),页面只负责展示和现算统计。

每句话各有用途(句子由导出脚本选定,切换按钮与数据文件一致,每句下方的说明也来自数据文件):

先猜,再看

在打开数据之前,先写下你的预测(写在纸上就行),看完再对照:

  1. 右上三角(未来位置)的权重会是多少?每一行的和呢?
  2. 越靠后的层,注意力图会更「散」还是更「尖」?
  3. 会不会有某个头几乎只看前一个 token?在第几层?
  4. 第一个 token 会不会像大模型那样吸走大量注意力(岔路 B4 的 attention sink)?

真模型:逐层逐头的注意力

真模型 · 项目小模型在几句话上的全部头(项目导出数据)
🎯

按顺序做:① 先看最上面的「数据自检」:未来位置的最大权重是否恰为 0、每行和是否为 1——这就是第 4 课的因果掩码和第 3 课的 softmax 在真模型上的样子,也是项目测试 test_attention_weights_are_causal 断言的东西;② 在几句话之间切换,找模式分数表里「看前一个 token」最高的那个头,点开它的大图:对角线下方那一条亮带就是「前一个 token」;③ 切到「話說天下大勢…」,点开几个后几层的头,看第二个「久」「必」所在的行:有没有头的亮点落在第一次出现的「久」「必」之后?④ 往下看第一个 token 的统计,和橙色基线比,回答预测 4。

读图的规矩。这些图只是一个小模型在几句话上的一次前向:每个格子是一个权重,不是一个解释。某个头在这几句话上「看前一个 token」,不代表它在别的文本上也这样;第一列很亮,不代表第一个词最重要(岔路 B4)。模式分数和基线都由组件对数据现算,页面上的结论句也是按数据生成的。

对照:浏览器里跑的真 GPT-2

我们的模型很小(层数、头数、参数量和验证 loss 显示在组件顶部)。换一个大得多的真模型对照:打开 Transformer Explainer,输入一句英文,逐个点开不同层、不同头的注意力。对照着看三件事:

  1. 它的注意力矩阵也都是下三角吗?(GPT-2 也是因果语言模型。)
  2. 12 个头的图案是不是各不相同?有没有「几乎只看前一个 token」的头?
  3. 很多头的第一列是不是特别亮?这就是岔路 B4 说的 attention sink 在 GPT-2 上的样子。

Transformer Explainer 用的是真实 GPT-2 small 权重在浏览器里的计算,不是示意图 。

怎么复现这份数据

数据由项目侧脚本生成(约定的路径是 04-实践项目/experiments/exp_c3_attention.py),读取 runs/<run_name>/ckpt.pt 与 data/processed/tokenizer.json,用模型的 return_attn=True 走手写注意力路径导出权重,再在验证集上统计第一个 token 的平均注意力,写入 知识平台/src/data/project/c3-attention.json。换一个配置重训(比如改 n_kv_head 或开 qk_norm)再导一次,就能看同一句话在不同模型里的图有什么变化。

⚠ 常见误解

⚠

「注意力图就是模型的『解释』:权重大的词就是模型做判断的依据。」注意力权重只说明这一层这一个头从哪些位置取回了多少 V;取回的内容还要经过 WO、FFN、后面几十层才影响输出,而且别的头、别的层可能在做完全不同的事。它是观察模型的一个窗口,不是模型推理过程的说明书 。

证据三问

  1. 它回答什么问题?前十课用手工向量讲的机制,在一个真训练出来的模型里是否成立、长什么样。
  2. 哪些是可证明的?未来位置权重恰为 0、每行和为 1——由掩码与 softmax 保证,页面的数据自检逐项核对 。
  3. 哪些只能看实验?每个头学成什么样、有没有 sink、有没有归纳头,都是这一个模型、这几句话上的观察,换模型换数据可能不同 。

一句话

机制是可证明的,长成什么样只能看实验:掩码与 softmax 在真模型上分毫不差,每个头学到什么,要一个一个去看。

下一步

本章到此结束。回 章首页 看项目验收清单与三档资料;下一章 C4 讲注意力取回信息之后,每个 token 自己还要做的加工:FFN、残差、归一化、门控。

你可能会问

这一课还没有收到真实提问;你的提问会记到 05-问答记录/C3-Lab.md。

🔍 贯穿例句为什么要配一句「玄德把劍給了關公」?

因为贯穿例句对这个模型来说是分布外的:训练语料是繁体古白话,「苹」「给」这类简体字在语料里几乎不出现,BPE 没为它们学到合并,只能切成两三个字节碎片。模型对这些碎片未必有像样的表示,注意力图可能和语料内的句子很不一样。所以配一句结构相同、人名和字形都来自语料的「玄德把劍給了關公」做对照。它也不完全是「见过的」:这个句式在语料里没出现过,「給」也还是两个字节碎片——两句切换着看,再和语料原句、验证集原句比,能大致分出哪些差别来自「字没见过」、哪些来自「句式没见过」。