看懂大模型推理优化,先认清三本账:Attention / KV、FFN / MLP 和系统调度

24 阅读16分钟

很多人看大模型架构时,会被 MoEMLAGQASliding Window AttentionPagedAttentionSpeculative Decoding 这些名词绕晕。其实只要主干还是 Transformer,大多数推理优化都逃不开三本账:Attention / KVFFN / MLP系统调度。本文试图用一套开发者能直接复用的框架,把这些看似五花八门的技术重新归类:它到底省的是算、读、存,还是把代价转移到了别处?

关键词: Transformer、Attention、KV Cache、FFN、MLP、MoE、MLA、GQA、Sliding Window Attention、PagedAttention、Speculative Decoding、推理优化、模型选型、部署成本

先看结论

  • 结论 1: 只要主干仍然是 Transformer,大模型推理就绕不开三本账:Attention / KVFFN / MLP系统调度
  • 结论 2: MoE 主要是在优化 FFN / MLP 账,降低每 token 激活计算,但不天然减少 KV cache。
  • 结论 3: GQAMLASliding Window Attention 主要是在优化 Attention / KV 账,减少长上下文下的存储、读取或计算压力。
  • 结论 4: PagedAttentionContinuous BatchingPrefix CacheSpeculative Decoding 更偏 系统调度 账,决定同一个模型能不能跑得更快、更稳、更便宜。
  • 结论 5: 所有优化都不是免费午餐。真正要问的不是“这个技术高级不高级”,而是“它把代价转移到了哪里,这个代价在我的目标下能不能接受”。

如果只用一句话概括全文:

看懂大模型推理优化,不要先背名词,先问它到底在优化哪本账。

一、为什么需要“三本账”这个框架

这两年看开源模型,会经常遇到这样的描述:

  • 671B total / 37B active
  • 1T total / 32B active
  • MoE
  • MLA
  • GQA
  • Sliding Window Attention
  • Hybrid Attention
  • PagedAttention
  • MTP
  • Speculative Decoding

这些词单独看都很有技术含量,但如果每个词都重新学一遍,很容易陷入碎片化。

你可能知道:

  • MoE 能让模型“每次只激活一部分专家”
  • MLA 能降低 KV cache
  • Sliding Window 能让模型只看局部窗口
  • PagedAttention 能提升并发

但真正做模型选型和部署时,更关键的问题其实是:

它到底省了什么?少算了?少读了?少存了?还是只是让调度更聪明了?

如果这个问题答不上来,就很容易出现误判。

比如:

  • 看到 active params 小,就以为显存门槛也小。
  • 看到 256K context,就以为长上下文一定便宜。
  • 看到 benchmark 高,就以为本地部署也一定顺。
  • 看到 MoE,就以为一定比 dense 快。
  • 看到 sliding window,就以为长距离能力一定没问题。

这些误判的共同原因是:

把模型能力、模型结构、资源成本和系统调度混在了一起。

所以我现在更习惯先把大模型推理拆成三本账。

Transformer 推理成本
≈ Attention / KV 账
+ FFN / MLP 账
+ 系统调度账

这三本账拆开之后,很多看似复杂的架构名词,会突然变得清楚很多。

二、先说底层:为什么这三本账是结构性存在

只要模型主干还是 Transformer,每一层大致都绕不开两块核心计算:

Attention block + FFN / MLP block

Attention 负责:

当前 token 怎么看上下文里的其他 token。

FFN / MLP 负责:

每个 token 自己怎么做非线性变换和表达扩展。

而当模型真正上线服务时,还会多出第三件事:

请求怎么排队、batch 怎么组、KV cache 怎么管理、多卡怎么通信、重复上下文怎么复用。

这就是系统调度。

所以这三本账不是某个模型的技巧,而是 Transformer 推理系统的底层会计科目:

Attention / KV 账:上下文交互要付多少钱
FFN / MLP 账:每个 token 自身变换要付多少钱
系统调度账:怎么把这些成本付得更聪明

只要这个结构不变,新的优化技术大多还是在这三本账之间移动成本。

三、第一本账:Attention / KV 账

Attention / KV 账主要回答一个问题:

模型看上下文这件事,到底要花多少钱?

在标准 self-attention 里,当前 token 需要和历史 token 的 K/V 交互。

生成阶段,也就是 decode 阶段,每生成一个新 token,都要读历史上的 KV cache。

所以长上下文和高并发时,Attention / KV 会变成非常现实的压力:

  • KV cache 占显存
  • decode 阶段要反复读 KV
  • 上下文越长,历史 K/V 越多
  • 并发越高,KV cache 总量越大

这本账主要影响:

  • 长上下文能不能跑
  • decode tokens/s 会不会随上下文下降
  • 显存是否被 KV cache 吃掉
  • 多并发时 KV pool 会不会撑爆
  • 长距离信息召回是否稳定

常见技术怎么归类

GQA 是在减少 KV head。

标准 MHA 里,每个 attention head 都有自己的 K/V。GQA 让多个 query head 共享一组 K/V,从而减少 KV cache。

它省的是:

少存 KV
少读 KV

代价是:

不同 head 的 K/V 表达没那么独立

MLA 是把 K/V 压缩成 latent 表示。

它不是简单减少 KV head,而是把需要缓存的 K/V 信息压缩成更紧凑的潜在表示,再按需要投影使用。

它省的是:

少存 KV
少读 KV
尽量保留多头表达能力

代价是:

结构和实现更复杂
训练、推理 kernel、框架支持要求更高

Sliding Window Attention 是限制大多数层能看的历史范围。

比如窗口大小是 1024,当前 token 主要看最近 1024 个 token,而不是全局都看。

它省的是:

少算 attention
少读远处 KV
长上下文成本更可控

代价是:

窗口外信息不能被局部层直接看到
需要 global attention 层或其他机制补偿

所以这些技术虽然名字不同,但都可以归到同一本账:

Attention / KV 账。

它们都在处理同一个核心矛盾:

模型越想完整看上下文,KV 成本越高;越想省 KV,就越要承担表达或召回上的代价。

四、第二本账:FFN / MLP 账

FFN / MLP 账主要回答另一个问题:

每个 token 经过模型自身变换时,到底要激活多少参数、读多少权重、做多少计算?

Transformer 一层里,除了 attention,还有很大一部分成本来自 FFN / MLP。

很多时候,FFN 甚至是每层计算的大头。

Dense 模型的特点是:

每个 token 基本都走同一套 FFN 参数

模型越大,每 token 激活计算也越大。

MoE 的思路则是:

总专家池很大,但每个 token 只路由到少数专家

这就是为什么模型卡里会出现:

1T total params / 32B active params
671B total params / 37B active params
25B total params / 4B active params

这里最容易误解。

active params 更接近:

每 token 实际参与计算的参数强度。

total params 更接近:

权重驻留、模型容量和部署门槛。

所以不能把 32B active 直接理解成:

这个模型只需要 32B 模型的显存。

它更准确的含义是:

这个模型总容量很大,但每个 token 激活的专家路径相对较小。

MoE 到底省了什么

MoE 主要省的是:

少算 FFN
少读被激活的专家权重
降低每 token active compute

但它不天然省:

KV cache
attention 范围
总权重驻留
专家通信和调度

这就是为什么我经常说:

MoE 主要优化 FFN / MLP 账,不是天然优化 Attention / KV 账。

如果你的瓶颈在每 token FFN 计算、权重读取、小 batch 利用率,那么 MoE 可能很有帮助。

但如果你的瓶颈在长上下文 KV cache,那么只靠 MoE 不一定能解决。

这也是为什么很多新模型会组合使用:

MoE + MLA
MoE + GQA
MoE + Sliding Window
MoE + Sparse Attention

因为它们分别在处理不同账本。

五、第三本账:系统调度账

系统调度账和前两本账不太一样。

前两本账更像模型结构本身:

Attention 怎么算
FFN 怎么算

系统调度账更像真实推理服务里的资源编排:

请求怎么排
batch 怎么组
KV cache 怎么管
重复 prompt 怎么复用
decode 怎么加速
多卡怎么通信
专家怎么分发

同一个模型,在不同推理框架里表现差很多,往往就是这本账不同。

比如:

  • Transformers 能跑,但服务吞吐不一定好。
  • vLLM 通过 PagedAttention 和 continuous batching 提升并发。
  • SGLang 在结构化生成、prefix/radix cache、agent 场景里更有优势。
  • KTransformers 可能在 MoE expert offload、异构推理上有特殊价值。

这些不是模型参数变了,而是:

系统调度变聪明了。

这本账主要优化什么

Continuous Batching 解决的是:

不同请求怎么动态合批,让 GPU 不要空等。

PagedAttention 解决的是:

KV cache 怎么像操作系统分页一样管理,减少碎片,提高并发容量。

Prefix Cache / RadixAttention 解决的是:

重复 prompt 能不能复用,不要每次重新 prefill。

Speculative Decoding 解决的是:

能不能用小模型或辅助头先草拟 token,再让大模型批量验证,减少逐 token 等待。

Expert Parallelism / DeepEP 一类机制解决的是:

MoE 专家分布在多卡上时,token 怎么分发、结果怎么收回,通信怎么不拖垮吞吐。

所以系统调度账不是“锦上添花”。

对于大模型服务来说,它经常决定:

  • 单请求是否顺滑
  • 多并发是否稳定
  • tail latency 是否可控
  • GPU 是否吃满
  • 长上下文是否能承载
  • MoE 是否真的跑出优势

一句话:

模型架构决定每个 token 理论上要付多少钱,系统调度决定这笔钱能不能被摊薄、复用、错峰、并行和隐藏。

六、把常见技术放回三本账

如果把常见技术重新归类,大概可以这样看。

Attention / KV 账

这一类主要管上下文交互和 KV cache:

  • MHA
  • MQA
  • GQA
  • MLA
  • Sliding Window Attention
  • Sparse Attention
  • Hybrid Attention
  • KV Cache Quantization

核心问题:

上下文看多少?
KV 存多少?
decode 时读多少?
长距离信息怎么保留?

FFN / MLP 账

这一类主要管每 token 激活计算:

  • Dense FFN
  • MoE
  • Shared Expert
  • Expert Offload
  • Expert Quantization
  • SwiGLU 等 FFN 结构选择

核心问题:

每个 token 激活多少参数?
读多少权重?
算多少 FFN?
专家调度复杂不复杂?

系统调度账

这一类主要管服务运行效率:

  • Continuous Batching
  • PagedAttention
  • Prefix Cache
  • RadixAttention
  • Speculative Decoding
  • MTP
  • Chunked Prefill
  • Expert Parallelism
  • Tensor Parallelism
  • Pipeline Parallelism

核心问题:

请求怎么排?
KV 怎么管?
重复上下文怎么复用?
多卡怎么切?
decode 怎么加速?

这张分类表最重要的价值不是记名词,而是帮你形成一个反射:

看到一个新技术,先问它属于哪本账。

七、用三本账分析几个典型模型

1. DeepSeek 路线

DeepSeek 这类模型通常可以理解成:

MoE -> 优化 FFN / MLP
MLA / 压缩 attention -> 优化 Attention / KV
推理框架并行与调度 -> 优化系统调度

它的核心思路不是只在一处省,而是同时处理:

  • 大容量模型如何不让每 token 计算爆炸
  • 长上下文下 KV cache 如何不要太重
  • 多卡和 MoE 专家如何调度

所以 DeepSeek 的架构描述里会频繁出现 MoEMLAactive paramsKV cache 这些关键词。

2. Gemma 4 26B A4B 路线

Gemma 4 26B A4B 这类模型更像:

MoE -> 优化 FFN / MLP
Sliding Window / Hybrid Attention -> 优化 Attention / KV
llama.cpp / vLLM / SGLang 支持 -> 影响系统调度

它的特点是:

  • 总参数比 active 参数大很多
  • 多数 attention 层用局部窗口降低成本
  • 少数 global attention 层保留长距离能力

所以你不能只看 25B total / 4B active,也不能只看 256K context

要问:

权重驻留能不能接受?
KV cache 在目标上下文下多大?
sliding window 是否影响业务里的远距离召回?
推理框架是否完整支持这个结构?

3. Kimi / MiMo 这类 Agent 模型

Kimi-K2.6、MiMo-V2.5-Pro 这类模型更明显地把三本账都摆在台面上。

比如:

MoE -> FFN / MLP 账
MLA 或 SWA/GA -> Attention / KV 账
INT4 / MTP / speculative / SGLang -> 系统调度账

它们的目标不是简单做一个聊天模型,而是支撑:

  • 长链路代码任务
  • 多步工具调用
  • 长上下文搜索
  • Agent swarm
  • 大量中间状态和长输出

这类模型如果只看能力 benchmark,很容易低估系统复杂度。

真正要看的是:

长链路中上下文怎么管理?
工具消息怎么裁剪?
多步调用 tail latency 怎么控制?
MoE expert 通信怎么调度?
长输出 decode 怎么加速?

这已经不是单纯模型问题,而是模型架构和推理系统一起的问题。

八、收益背后一定有代价

三本账框架背后还有一个更底层的原则:

收益背后必有代价。

更准确地说:

优化不是消灭代价,而是把代价重新安排到更适合当前目标的位置。

举几个例子。

MoE 的收益是:

总容量更大
每 token active compute 更低

代价是:

专家路由
专家通信
调度复杂度
权重驻留仍然很大

Sliding Window Attention 的收益是:

attention 成本更低
KV 读取范围更小
长上下文更可控

代价是:

窗口外信息召回需要其他机制补偿
某些全局推理任务需要实测

MLA 的收益是:

KV cache 更小
长上下文 decode 更友好

代价是:

架构复杂
训练和推理实现复杂
框架支持要求高

量化 的收益是:

权重更小
显存更省
带宽压力更低

代价是:

精度风险
kernel 支持依赖
不同任务稳定性需要验证

系统调度 的收益是:

吞吐更高
资源利用率更好
重复上下文可复用

代价是:

实现复杂
tail latency 管理更难
不同负载下表现不稳定

所以成熟的判断不是问:

有没有代价?

而是问:

这个代价我是否看得见、算得清、承受得起,并且值得为目标支付?

九、如何用三本账分析一个新模型

以后看到一个新模型,我建议按下面步骤看。

第一步:先看基础结构

先找这些字段:

total params
active params
num layers
num attention heads
num KV heads
attention mechanism
context length
expert count
experts per token
precision / quantization
recommended engine

这一步不是为了背配置,而是为了判断:

它在哪本账上动了刀?

第二步:把架构归到三本账

例如:

MoE -> FFN / MLP
MLA -> Attention / KV
GQA -> Attention / KV
Sliding Window -> Attention / KV
INT4 -> 权重驻留 / 带宽
PagedAttention -> 系统调度
Speculative Decoding -> 系统调度 / decode 加速

第三步:问它省了什么

不要只写“更高效”,而要写:

少算?
少读?
少存?
少通信?
更好调度?

比如:

  • MoE:少算 FFN,少读被激活专家权重。
  • MLA:少存少读 KV。
  • GQA:少存少读 KV head。
  • Sliding Window:少读远距离 KV。
  • Speculative Decoding:减少主模型逐 token decode 步数。

第四步:问代价转移到了哪里

每个收益都对应代价。

你要继续问:

质量风险在哪里?
工程复杂度在哪里?
框架依赖在哪里?
调度风险在哪里?
长上下文召回风险在哪里?

这一步决定你是不是只被模型卡牵着走。

第五步:设计最小压测

如果你关心部署,不要停留在口头判断。

最小压测可以先做两组。

第一组是 context scaling

1K / 8K / 32K / 128K prompt
固定输出长度
固定并发

看:

TTFT 怎么变
decode tokens/s 怎么变
显存峰值怎么变

第二组是 batch scaling

固定上下文
固定输出长度
batch 1 / 4 / 8 / 16

看:

总吞吐是否提升
单请求速度是否崩
tail latency 是否变差

判断口径很简单:

上下文敏感 -> Attention / KV 账更可疑
batch 敏感 -> 权重读取 / FFN / 调度更可疑
两者都敏感 -> 混合瓶颈
两者都不敏感 -> 查服务链路、框架实现或其他开销

十、这套框架适合解决什么问题

三本账不是为了替代 benchmark,而是为了让你看 benchmark 更有方向。

它特别适合回答这些问题:

  • 为什么一个 MoE 模型总参数更大,实际吞吐反而更高?
  • 为什么一个模型支持 256K,但本地长上下文还是很慢?
  • 为什么同一个模型在 vLLM、SGLang、llama.cpp 里表现差很多?
  • 为什么有的模型 batch 一上来就吞吐提升,有的反而崩?
  • 为什么量化后显存省了,但质量或速度不一定线性变好?
  • 为什么长链路 Agent 不只是模型能力问题?

这些问题表面不同,本质都是:

成本到底落在哪本账上?

十一、最后总结

我现在看大模型架构,越来越不愿意先问:

这个技术是不是最新?

而是先问:

它到底在优化哪本账?

只要主干还是 Transformer,大多数推理优化都可以先放进这三本账:

Attention / KV:上下文怎么被看见,KV 怎么被存和读
FFN / MLP:每个 token 激活多少参数,读多少权重,做多少计算
系统调度:请求、batch、KV、缓存、多卡和 decode 怎么被组织

理解这三本账之后,很多名词就不再是孤立知识点。

MoEMLAGQASliding WindowPagedAttentionSpeculative Decoding,本质上都在回答同一个问题:

在目标约束下,如何重新配平收益和代价?

所以,真正成熟的模型选型不是追逐“最强模型”,而是看清:

我的目标是什么?
当前瓶颈在哪里?
这个方案带来的收益是否贴近目标?
它把代价转移到了哪里?
这个代价我是否能接受?

如果这几个问题能回答清楚,你看任何新模型、新架构、新推理框架时,都会比只看榜单和宣传语稳得多。

最后用一句话收束:

所有工程优化,都是收益和代价的重新配平。看懂收益不难,看清代价转移,才是真正的判断力。