从0训练LLM(旧版 · 存档中) · M6 阅读+实验 ≈ 70 分钟 页内实验 ×2

推理与现代架构

模型训好了,怎么让它又快又省地跑起来?推理阶段有一整套和训练完全不同的工程。主线是一个瓶颈——KV cache——以及围绕它演化出的现代架构:GQA/MLA 压缓存、MoE 稀疏激活、PagedAttention 管显存、量化和投机解码提速。
① 主线定位

训练是一次性的,推理是每天的

M1-M5 把模型训出来了。这一节讲怎么让它高效地服务。

前面五个模块解决的是“怎么训出一个模型”。但模型训好只是一次性投入,真正每天在烧钱的是推理——每一次对话、每一个 token 的生成。推理阶段的工程目标和训练完全不同:不是让 loss 下降,而是在有限显存里,尽可能快、尽可能多地服务请求。

🧭

上游: M1-M5 训练好的模型权重。
本节: 推理的核心瓶颈(KV cache)+ 围绕它的现代架构(GQA/MLA、MoE)+ 推理系统(PagedAttention、continuous batching)+ 提速手段(量化、投机解码)。
下游: 这是本课程主线的终点——你已经从分词一路走到了能把模型高效跑起来。

② 核心问题

推理为什么会慢、会爆显存?

一个词:KV cache。理解它,就理解了现代架构一半的设计动机。

自回归生成是一个 token 一个 token吐出来的。每生成一个新 token,都要让它和前面所有 token 做注意力(用它们的 K 和 V——M2 亲手算过的那两个向量)。如果每次都把前面所有 token 的 K、V 重新算一遍,计算量会爆炸。

解决办法是KV cache:把每个 token 算过的 K、V 缓存下来,生成下一个时直接复用。下面亲手生成一遍,两种模式对比着点:

动画 · 逐 token 生成:开关 KV cache 对比(真实记账)

🎯

两种模式各点完一整句:无缓存模式每步所有旧 token 都闪橙(全部重算),计算量按 3+4+5+…累加;有缓存每步只算 1 次。一句 9 个词的话就差 6 倍多,生成 1000 个 token 时差距是几百倍——这就是 KV cache 不可不用的原因。

但缓存不是免费的——它引入了新问题:这些 K/V 全躺在显存里,随序列变长线性膨胀,很快吃光显存。(顺带说明:M2 推荐过的 bbycroft.net/llm 3D 可视化里没有 KV cache——它演示的是每步重走全流程,正是上面”无缓存”模式。所以这个概念只能在这里亲手看。)

顺带补上生成的最后一步:温度与采样

自回归的每一步,模型输出的其实是整个词表的概率分布,真正吐出哪个词要靠采样。用户能调的那个「温度 T」,改的就是这个分布的形状——softmax(logits / T):

三联动 · 温度改的是什么(真算术)
模型读完「今天天气真」,输出层给出 5 个候选的 logits(原始分数)。生成前的最后一步:softmax(logits / T) 变成概率,再从中采样。
0.1 确定1.02.0 随机
① logits(不随 T 变)
② softmax(logits/T) 概率
③ 分布的随机性
熵 = bits

🎯

关键观察:左图(logits)从头到尾一动不动——温度不改模型的判断,只改分布的形状。T→0 塌缩成确定输出(每次都一样),T→2 趋于均匀(开始胡说)。这和 M2 的 √d_k 是同一个数学:都是”除一个数再过 softmax”,√d_k 是训练时的固定温度,T 是推理时你手里的旋钮。

❓

于是推理的核心矛盾就成了:KV cache 又不能不要(否则重复计算慢死),又会把显存撑爆。现代架构里一大半的创新——GQA、MQA、MLA、PagedAttention——都是在跟这个 KV cache 较劲。下面的实验让你亲手看它怎么膨胀、又怎么被压下去。

③ 原理 · 直说

围绕 KV cache 的四类招数

压缓存、稀疏激活、管显存、抄近路——现代推理的四条线。

招数一:压 KV cache —— GQA / MQA / MLA

既然 KV cache 是瓶颈,最直接的想法就是让它更小。标准的多头注意力(MHA)里,每个注意力头都存自己的一份 K、V。但其实——多个 query 头可以共享同一组 K、V:

  • MQA:所有 query 头共享 1 组 K/V,压得最狠,但表达力略降。
  • GQA:折中,把头分成几组、每组共享一组 K/V。实测几乎无损,现代大模型几乎都用它。
  • MLA(DeepSeek):更进一步,把 K/V 压成一个低秩的“潜向量”,KV cache 再降一个数量级。

MLA 的“压”不是玄学,就是三行矩阵乘法——和 M4 的 LoRA 是同一个低秩思想,只是用在了缓存上:

MLA 的核心:缓存的不是 K/V,是压缩包 c
= ; kt = , vt =
👆 公式里带下划线的每一项都可以点——点哪项,讲哪项。
对比记账(每 token 每层):MHA 存 2·n_h·d_h 个数 → GQA 存 2·n_kv·d_h(少几倍)→ MLA 只存 r 个(少一个数量级)。代价是每步多两次小矩阵乘(升维),拿计算换显存——推理瓶颈在显存带宽,这笔交易稳赚。

下面的可视化让你调层数/头数/序列长度,直接对比三者的 KV cache 大小。

计算器 · KV cache 与 MHA/GQA/MQA(真实算术)
KV cache 随序列长度线性增长——三条线的斜率就是三种方案的差距。竖虚线 = 你当前拖到的序列长度。

招数二:稀疏激活 —— MoE

另一条线是让模型大而不贵。MoE(专家混合)把一层的前馈网络换成很多个“专家”,但每个 token 只经过路由器选中的 top-k 个专家。整层的计算写出来只有两行:

MoE 层的计算(替换掉 M2 里的那个 FFN)
= softmax((x·Wg)) ; y = Σi∈TopK
👆 公式里带下划线的每一项都可以点——点哪项,讲哪项。
下面的工具就是这两行公式在跑:点一个 token → 路由器打分 → top-k 高亮 → 只有紫色专家参与计算。

GLM/DeepSeek-V3 这类都是几百个专家、只激活个位数(约 5% 稀疏)。下面的工具让你点 token 看它激活哪些专家。

可视化 · MoE 路由与稀疏激活
整句 7 个 token 的累计负载(每个专家被激活几次):

真模型 · 看 Gemma 2 的真实专家路由

上面是示意路由。MoE Expert Routing Visualiser 用的是 Gemma 2 真实的路由数据:选一个领域(写作/经济/历史/软件工程),逐 token 看每一层实际激活了哪些专家,还有累积热力图——少见的用真实模型数据而非示意图做的路由可视化。

👀

看什么: ① 同一个专家会不会跨领域被激活(会——专家不是按”学科”分工的,是按更细的 token 模式);② 换领域后热力图的分布变化;③ 右边那个计算器可以拿真实模型(Llama-3 等)验证你在上面 KV cache 计算器里算出的量级。

招数三:管显存 —— PagedAttention

KV cache 在显存里是连续分配的,导致大量碎片浪费(现有系统利用率一度只有 20-38%)。PagedAttention(vLLM)借鉴操作系统的虚拟内存分页:把 KV cache 切成小块按需分配、按块映射,碎片几乎消除,吞吐提升 2-4 倍。配合 continuous batching(按迭代级动态替换已完成的请求,而不是等整批做完),GPU 利用率再上一个台阶。

“碎片浪费”和“分页解决”这两句话很抽象。下面这条显存条把两种方案摆在一起,同一批请求、同一块显存,利用率两边都真算:

模拟器 · 分页 vs 连续分配(真算术)
请求1(最长 16 token) 请求2(最长 16 token) 请求3(最长 16 token) 请求4(最长 24 token) 预留但没写 = 浪费 空闲
显存池共 32 个 block;1 格 = 1 个 block = 2 个 token(vLLM 实际默认 16 token/block,这里缩小是为了看清)。请求的最大长度各不相同——这正是连续分配产生碎片的根源。
方案 A · 连续预分配 每个请求按最大长度整段预留,中途不能挪 —
方案 B · PagedAttention 分页 按需逐块发,block 不必连续,页表负责串起来 —
请求 1 —
请求 2 —
请求 3 —
请求 4 —

两种碎片,一次说清:内部碎片=按最大长度预留却没写满(上面的斜纹);外部碎片=释放后留下的空洞拼不成连续段(上面请求4 失败的原因)。vLLM 论文(SOSP 2023)实测:预分配式的推理系统里,真正存着 token 的显存只占 KV cache 显存的 20–38%,其余全被这两种碎片吃掉。分页把两者同时干掉——它唯一剩下的浪费,是每个请求最后那个没填满的 block(上面的半格),最多半个 block。省下的显存直接变成更大的 batch,这才是 vLLM 吞吐 2–4× 的来源。出处: /papers/S6-05-vLLM-PagedAttention.pdf

🎯

试三件事: ① 什么都别点,先看方案 A 的利用率——20.8%,正好落在 vLLM 论文实测的 20–38% 区间里,浪费的全是“万一它写到最大长度呢”的预留(斜纹);② 猛点几下「生成一个 token」,看斜纹一格格被吃掉、A 的利用率慢慢往上爬——连续预分配只有在请求刚好写满最大长度时才不亏,而实际长度事先根本不知道;③ 点「请求2 完成 · 释放」再点「新请求4 进来」:A 有 16 格空闲、却放不下一个要 12 格的请求(凑不出连续段),B 直接把空洞捡回来用。这就是 2-4 倍吞吐的来源。

招数四:抄近路 —— 量化 / 投机解码 / 蒸馏

中间那条——又快 2-3 倍、输出还完全不变——听起来像白捡的。它不是魔法,把一轮的“猜 → 一次验完 → 接受/拒绝”逐格走一遍就清楚了:

步进 · 投机解码:猜 4 个、验 1 次(真算术)
最终输出(9 个 token)—— 每一格标注它是被接受的猜测还是target 给的 bonus
· 未生成
· 未生成
· 未生成
· 未生成
· 未生成
· 未生成
· 未生成
· 未生成
· 未生成
第 1 轮 · 点下面的按钮开始
? draft 猜
? draft 猜
? draft 猜
? draft 猜
+
? target bonus
大模型前向0次
已生成 token0个 / 共 9
加速比—× vs 逐 token
逐 token 生成
9 次前向
投机解码
0 次前向

说明:上面演示的是贪心(温度=0)下的简化版。严格的无损性来自接受-拒绝采样:draft 给出分布 q、target 给出 p,以概率 min(1, p/q) 接受该 token,拒绝时从归一化后的 (p − q)+ 重新采样。可以证明这样得到的最终分布与「直接从 target 采样」完全相同;每个 token 的期望接受率就是 Σx min(p(x), q(x))。贪心解码下「分布一致」正好退化成「token 相等」,也就是上面在做的事。完整证明见 Leviathan et al. 2023,本地论文库 /papers/S6-09-Speculative-Decoding.pdf。

K3 注脚:Kimi K3 不再挂一个独立的小模型当 draft——它在预训练时就带了一层 MTP(multi-token prediction)层,结构和主干块一致;后训练时冻住 target,把这层 MTP 微调成 EAGLE-3 式的 draft(输入融合了主干第 1、4 和最后一个 AttnRes 块的低/中/高层特征),训练时 draft 一次展开 7 步。draft 与 target 共享同一套表示,猜得更准 → 接受率更高 → 上面那个「加速比」更大。报告里还专门讲了它和 KDA 的冲突:递归状态是原地更新的,一旦验证拒绝就回滚不了,K3 的解法是只缓存 draft token 的投影输入、在片上重建被接受前缀的状态。

🎯

试三件事: ① 连点三次「跑一轮」把 9 个 token 走完,盯住加速比:4.00 → 2.50 → 3.00——它就是「已生成 token ÷ 大模型前向次数」,每一步都真算;② 单看第 2 轮,draft 第一个就猜偏、四个猜测一个都不留,但这一轮照样产出 1 个 token(target 的这次前向顺手把正确答案算出来了)——这就是投机解码的下界:最坏情况等于逐 token 生成,永远不会更慢;③ 数一数最终那 9 格的标注,几个是“draft 猜中”、几个是“target 给出”——bonus 是白拿的,所以每轮产出 = 接受数 + 1,永远落在 1 到 k+1 之间。

🔍 前沿:DeepSeek-V4 / GLM-5 在做什么

2026 年的前沿都在“稀疏注意力 + 极致压 KV”上卷。DeepSeek-V4 用 CSA(把每 m 个 token 的 KV 压成一条再做稀疏注意力)+ HCA,1M 上下文下相比 V3.2 只要约 27% 的算力、10% 的 KV cache。GLM-5 用 MLA + DSA(在 MLA 上加检索器只对 top-k 相关 KV 做注意力)。本质都还是本节这四类招数的延续:压缓存、稀疏化。

④ 亲手实验

两个可视化,看懂现代架构的动机

KV cache 怎么被压、MoE 怎么稀疏。

  1. KV cache 计算器:把序列长度拉满,看 MHA 的 KV cache 怎么膨胀;再切 GQA/MQA,看它降到几分之一。
  2. MoE 路由:调专家总数和 top-k,点不同 token 看激活哪些专家,理解“总参数大、激活参数小”。
⑤ 项目推进 · 从 0 搭

把我们的模型高效跑起来

不用自己造推理引擎,学会用最好的那个。

本模块的项目任务单

步骤你的决策 / 动作说明
1. 用 vLLM 部署让 AI 用 vLLM 加载我们训好的模型PagedAttention + continuous batching 开箱即用
2. 观察 KV cache跑长/短上下文,看显存占用差异对应上面的 KV cache 计算器
3.(可选)量化用 GPTQ/AWQ 量化到 4-bit,对比显存与质量省显存的代价是轻微质量损失
4.(可选)投机解码配一个小草稿模型看吞吐提升、确认输出不变
5. 验收测吞吐(tokens/s)和首 token 延迟理解这两个指标各受什么影响
🎓

到这里,整条主线走完了。 从 M1 把文字切成 token,到 M2 搭注意力、M3 预训练、M4 教它回答、M5 对齐偏好,再到 M6 高效推理——你已经把一个现代大模型从 0 到能用的每一环都亲手过了一遍。剩下的是在这个骨架上不断加深。

⑥ 坑与带走

常见的坑 + 该带走的

坑症状怎么办
不用 KV cache每个 token 重算全部注意力,慢到不可用必开 KV cache
以为 KV cache 免费长上下文直接爆显存它随序列线性增长,是头号瓶颈
MHA 用到底KV cache 太大、吞吐低用 GQA(几乎无损)甚至 MLA
手写推理循环显存碎片、吞吐差用 vLLM(PagedAttention + continuous batching)
用 bbycroft.net/llm 学 KV cache那个可视化里根本没有 KV cache它每步重走整个流程、无缓存概念,学 KV cache 得用别的
量化后不测质量悄悄掉点量化必须配质量评测

这一模块你应该带走的

🔭

概念索引(本模块登场): 自回归生成 · KV cache · MHA/MQA/GQA/MLA · 低秩压缩 · MoE · 路由器 · top-k 稀疏 · PagedAttention · 虚拟内存分页 · continuous batching · 量化 GPTQ/NF4 · 投机解码 · 知识蒸馏 · 暗知识

💬

有不明白的? 随时在对话里问我,我会记到 05-问答记录/M6-推理与架构-问答.md。

深入这一模块

想往下钻,按你愿意花的时间选

⚠️ 提醒:bbycroft.net/llm 那个热门可视化里没有 KV cache(它每步重走整个流程),学 KV cache 别用它。

🎮 想更直观 10–30 分钟

动手工具,比读文字管用
10-15 min英文需联网
用 Gemma 2 真实路由数据,逐 token 展示每层激活了哪些专家,带累积热力图。
少见的用真实模型数据而非示意图做的路由可视化,正好讲 MoE 的“总参数大但激活少”。
10 min英文需联网
实时公式计算显存(2(K+V)×FP16=4096 bytes/token/layer),可切模型预设/精度。
实测可用、公式可见非黑箱。缺点:层数/头数不能独立手调。
10 min中文需联网
vLLM + KV Cache + PagedAttention 内部原理速览。
快速建立“vLLM 为什么快”的直觉。

🔬 想吃透原理 1–3 小时

苏剑林那篇是 GQA/MLA 演进的主心骨
长文含推导中文需联网 40 万+ 阅读
用数学推导讲清 MHA→MQA→GQA→MLA 每一步“省了什么、牺牲了什么”,而非只给结论。
苏神是公认“讲清为什么而非贴结论”的作者。M6 讲 GQA/MLA 演进的主心骨。
长文英文需联网
GShard→Switch→ST-MoE 演进,含负载均衡、容量因子、块稀疏矩阵可视化。
MoE 最权威的英文综述,有实证表格。
长文中文需联网
给出 KV Cache 优化的四层分类法:架构层(GQA/MLA)、系统层(PagedAttention/Continuous Batching)、量化层、稀疏层。
少见的把 M6 所有子概念放进统一分类框架,适合建全局地图。
中长文英文需联网
PagedAttention 把 KV cache 当虚拟内存分页管理,减少 55% 内存、2.2x 吞吐。
一手官方博客含实证数字。

📄 想读原文 按需

PDF 已在本地 01-论文库/
SOSP 2023
现有系统 KV cache 利用率仅 20-38%,借鉴 OS 虚拟内存分页,吞吐 2-4x。
EMNLP 2023 / 2024
GQA 用 5% 原始算力把 MHA uptrain 成 GQA;MLA(DeepSeek-V2)把 KV 压到低秩潜向量,KV cache 减少 93.3%。
2021 / 2022
Switch 把 top-k 简化为 top-1、预训练提速最高 7x;投机解码在 T5-XXL 上 2-3x 加速且输出分布完全不变。
🚫

我替你排除了什么: 各类 KV Cache 计算器(WebFetch 403 / navigate 超时,无法实测确认)· INT4/INT8 英文 SEO 聚合文(同质化转载)· glm5.net 等产品推广站 · “5 分钟学会推理加速”速通向。
重要纠正:bbycroft.net/llm 那个热门 3D 可视化里没有 KV cache——它每步“重新走整个流程”,是理解 self-attention 本身的好工具(属 M2),但学 KV cache 会误导。

← M5 对齐与强化学习 M7 前沿解剖:读懂 Kimi K3 技术报告 →