KV Cache 与推理优化:生成快的秘密
本文基于模型知识整理(生成时未联网核对),PagedAttention 与 MQA/GQA 建议对照 vLLM 论文与 GQA 论文复核。
一句话定义
自回归生成时每步都对全部历史重算注意力——KV Cache 把每个 token 的 K/V 缓存复用(每步只算新 token 的 Q),把每 token 成本从 O(n²d) 降到 O(nd);代价是缓存随长度线性增长吃显存——MQA/GQA(共享 KV 头)、PagedAttention(分页管理)、量化缓存是治理这一"显存税"的三板斧。
为什么重要
推理是 LLM 的常驻成本(训练一次、推理亿次):KV Cache 的显存占用常超过模型权重本身(长上下文时数倍),直接决定"单卡能跑多长上下文、并发多少用户"。vLLM 的 PagedAttention 把吞吐提升 2~4 倍成为推理基础设施标配——理解 KV Cache 是读懂一切推理优化的前提。
前置知识
kp-002/003(QKV 与多头)、kp-005(复杂度)。
核心概念
- 没有 Cache 的浪费:生成第 t 个 token 时,前 t−1 个 token 的 K/V 与上一步完全相同(因果掩码下历史不变)——朴素实现每步重算全部历史的 K/V,O(n²d) 的重复劳动。
- KV Cache 机制:逐步追加存储 $K_{1:t},V_{1:t}$;新 token 只算自己的 $q_t,k_t,v_t$,与缓存做注意力($O(nd)$/步)。prefill 与 decode 两阶段:prompt 整段并行算(prefill,一次付清)→ 之后逐 token(decode,带宽受限)。
- 显存账本:KV 大小 = 2(K与V)× 层数 × KV头数 × 头维 × 序列长 × 精度字节。例:70B 模型(80 层、8 KV头、128 维、fp16)每 token ≈ 320KB——4k 上下文 1.3GB/请求;并发与长上下文在此相乘爆显存。
- 治理三板斧:
- MQA/GQA:多个 Q 头共享 1/8 组 KV(Llama-2 70B 用 GQA-8)——缓存 ÷8,质量损失微小; - PagedAttention(vLLM):像操作系统分页一样管理 KV 显存(消除碎片、共享前缀——系统提示只存一份)——吞吐 2~4 倍; - KV 量化:缓存本身压到 8bit/4bit(精度换显存,kp-024 思想在推理侧的移植)。
- 两大阶段的不同瓶颈:prefill 是计算受限(并行算长 prompt)→ 算力瓶颈;decode 是带宽受限(每步都要读全部 KV 与权重,算术强度低)→ 显存带宽是生成速度的真正天花板(kp-005 带宽分析的推理版)。
原理与机制
为什么 decode 是带宽受限:每生成 1 个 token 要读一遍全部权重(几 GB~几百 GB)+ 全部 KV——算术强度(FLOPs/字节)很低,GPU 算力大量闲置等数据。吞吐优化的本质=把更多请求的解码打包在一起共享权重读取(continuous batching 的原理)。
为什么 GQA 几乎免费:KV 头减少=缓存与带宽 ÷8;多头注意力(kp-003)的信息混合由 Q 头保持——"Q 的多样性 × KV 的共享"权衡实证上损失很小。这是推理经济学对架构的直接改造(MQA 极端版、GQA 折衷版的演进)。
共享前缀的乘法效应:多用户共享同一系统提示(几 k token)——PagedAttention 让这些前缀的 KV 物理共享(写时复制)——系统提示越长,分页共享的省越惊人。
图示
无Cache: 每步重算全历史K/V → O(n²d) 累计 (浪费)
KV Cache: 缓存K/V, 每步只算新token → O(nd)/步
两阶段: prefill(prompt并行算) + decode(逐token)
显存: KV = 2·层·KV头·头维·n·bytes
例70B/4k ≈ 1.3GB/请求 → 长上下文爆显存
三板斧: GQA(÷8) | PagedAttention(吞吐2~4×) | KV量化
decode瓶颈 = 显存带宽 (非算力) → batching共享权重
直观类比
没有 KV Cache 的模型像"写小说写到第 500 章,每写一句都把前 499 章重读一遍"(重算);KV Cache 像"给前文贴好便签索引"——写新句只需翻便签。GQA 像"多个作者共用一个资料室"(共享 KV);PagedAttention 像"图书馆分页管理书架"——碎片不再浪费、公共藏书只放一份。
实例或案例
- vLLM:PagedAttention + continuous batching——开源推理服务的事实标准(吞吐提升的公开 benchmark)。
- Llama-2 70B 的 GQA-8:KV Cache ÷8,质量损失在评测噪声内——架构为推理让路的工业决策。
- 长上下文定价:API 按输入/输出 token 差异定价——prefill(算力)与 decode(带宽)成本结构的市场映射。
常见误区
- 误区一:"KV Cache 改变了计算结果"。数值完全一致(缓存的 K/V 与重算相同)——纯优化无近似。
- 误区二:"生成慢是因为算力不够"。decode 阶段算术强度低,瓶颈是带宽;加算力卡不如加带宽/加大 batching(选卡逻辑由此而来)。
- 误区三:"上下文越长速度线性慢一点而已"。KV 显存线性涨→并发容量线性降;长上下文的成本是非线性服务的(分页/量化/GQA 是必需品不是奢侈品)。
与其他知识点的关系
自测题
- KV Cache 把每步生成成本从什么降到什么?
答:从 O(n²d)(重算全历史注意力)降到 O(nd)(新 token 的 Q 与缓存 K/V 相乘)。
- GQA 省的是什么?代价是什么?
答:省 KV Cache 显存与带宽(÷共享倍数);代价是 KV 表达多样性下降——实测质量损失微小。
- 为什么 decode 阶段加 GPU 算力收益有限?
答:decode 是带宽受限(每步读全权重与 KV,算术强度低)——提升吞吐靠 batching/共享前缀,而非纯算力。
延伸阅读
- Kwon 等, "Efficient Memory Management for LLM Serving with PagedAttention"(SOSP 2023,vLLM)。
- Ainslie 等, "GQA: Training Generalized Multi-Query Transformer"(2023)。
- 《How do LLMs generate text》类推理拆解博客(prefill/decode 两阶段的可视化)。