01-vLLM-PagedAttention与连续批处理技术拆解

发布时间:2026/9/6 10:24:41
01-vLLM-PagedAttention与连续批处理技术拆解 vLLM 推理加速的双引擎PagedAttention 与 Continuous Batching 技术拆解与生产调优原创 · 大模型推理专栏 | 全文约 3000 字预计阅读 10 分钟部署过大模型服务的工程师都有过类似的困惑模型权重明明只有 14GBLlama-2-7B 的 FP16 权重把服务跑起来却发现 80GB 的 A100 剩不下多少空间并发一上来就 OOM。问题不在权重而在 KV Cache。一、一张请求的显存账本KV Cache 为什么是大模型推理的命门Transformer 解码是自回归的生成第 N 个 token 时需要用到前 N-1 个 token 的 Key 和 Value 向量做 Attention。这些向量不会随解码过程消失而是要在整个生成周期里反复参与计算。把它们缓存下来就是 KV Cache。KV Cache 的体量可以精确计算公式很简单单 Token KV 显存 2K、V 两份 × 层数 × KV 头数 × 头维度 × 字节数 Llama-2-7BMHA32 个 KV 头2 × 32 × 32 × 128 × 2B 512 KB / token 一条 2048 token 的请求 ≈ 512 KB × 2048 1 GB Llama-3-8BGQA8 个 KV 头2 × 32 × 8 × 128 × 2B 128 KB / token 一条 4096 token 的请求 ≈ 512 MB一条请求就是 GB 量级一个 32 并发的小服务光 KV Cache 就要吃掉几十 GB。而且这个数字随序列长度线性增长长上下文场景下 KV Cache 会成为比权重更贵的资源。这也是为什么 DeepSeek 的 MLA多头潜在注意力要把 KV 压缩成低秩潜变量——KV Cache 的优化空间直接决定推理成本。二、传统 Serving 系统的三大浪费在 PagedAttention 出现之前主流推理框架管理 KV Cache 的方式可以概括为三个字预分配。这种模式存在三类浪费静态预留请求进来时按最大可能长度或 max_seq_len一次性分配一整段连续显存而绝大多数请求实际生成的 token 远小于上限预留空间长期闲置。内部碎片Batch 内所有序列共享同一个内存池每个序列按自己当前长度占用空间长度参差导致池内出现大量无法合并的小空洞。外部碎片请求先后结束、释放内存后留下的空洞位置分散新请求无法利用只能继续向 GPU 申请新内存最终把显存申请爆。论文在单张 A100 上跑 Llama-7B 的实测数据触目惊心HuggingFace Transformers 的 KV Cache 内存浪费高达 73%FasterTransformer 也有 50%而 vLLM 只有 4%1。三、PagedAttention把操作系统的分页思想搬进 GPUPagedAttention 的核心洞察很朴素既然操作系统虚拟内存能用页表解决连续分配 碎片整理的问题KV Cache 为什么不能答案是完全可以。3.1 逻辑块与物理块vLLM 把 KV Cache 划分成固定大小的块block默认 16 个 token 一块。每个序列持有逻辑块通过一张 Block Table 映射到显存中任意空闲的物理块这样带来的直接收益有三个按需分配一个 token 生成出来才占用一个 slot请求结束立即释放整块不再有预分配一大段的浪费。碎片消失物理块可以散落在显存任意位置不存在必须连续的约束外部碎片问题从根上被消灭。共享成为可能多个请求如果前缀相同可以共享同一批物理块这是后续 Prefix Caching 的地基。3.2 Block Table 的数据结构每个序列维护一张 block table形如逻辑块 0 → 物理块 3 逻辑块 1 → 物理块 11 逻辑块 2 → 物理块 7生成过程中每当新 token 填满一个逻辑块vLLM 的 scheduler 就从显存池中申请一个新物理块把映射追加进表里。整个映射关系由 scheduler 统一维护属于典型的内存管理下沉到 Serving 层的设计。3.3 按块计算分块 Softmax 的数学正确性Attention 计算在这里遇到一个麻烦标准 softmax 需要全局的 max 和 sum而 PagedAttention 的 KV 数据是分块存放的无法整段读入。它的解法是分块 softmax每个块先独立计算局部 softmax并记录块级统计量局部最大值 m 和归一化因子 l最后用类似 FlashAttention 的 rescale 技巧合并——数学上精确等价于全局 softmax只是把全局归约拆成了块内计算 跨块合并。FlashAttention 论文早已解决过这个问题PagedAttention 把同一思想从连续内存推广到了分页内存。后来 vLLM 与 FlashAttention 深度集成支持分页 KV Cache 的 flash paged attention kernel单卡吞吐又上了一个台阶。3.4 前缀共享与 Copy-on-Write分页设计还顺带解锁了一个高频场景parallel sampling一次请求同时生成 N 个候选。N 个序列共享同一段 prompt如果它们共享同一批物理块KV Cache 占用就从 N 份降到 1 份。vLLM 用引用计数 Copy-on-Write 实现共享块只读一旦某个序列要写入共享块先复制再修改。这在多轮对话system prompt 历史轮次反复出现和 beam search 场景收益巨大也是 vLLM 后续 Prefix Caching 特性的底层基础。四、Continuous Batching让 GPU 一刻也不闲着PagedAttention 解决了内存怎么放Continuous Batching连续批处理解决谁先谁后。4.1 静态批处理的气泡早期框架的做法是静态批处理static batching一批请求同时开始、同时结束。问题是 batch 内各请求长度差异巨大——短的 20 秒跑完却要等长的跑完才能释放显存和算力GPU 上出现大量气泡bubble。调度粒度过粗是吞吐上不去的根本原因。4.2 迭代级调度OrcaOSDI 2022提出了迭代级调度iteration-level scheduling2调度粒度从整个请求细化到一次前向传播。每个 decode 步骤结束后scheduler 重新决定下一轮谁参与计算完成的请求立即退出腾出的 KV Cache 马上分配给新请求新请求可以在任意时刻加入不需要等一个 batch 跑完。vLLM 的 scheduler 在每个 step 检查两个队列running正在计算和waiting等待中。只要显存池还有空闲块就把 waiting 里的请求拉进 running。效果就是 GPU 利用率曲线从锯齿状变成满负荷。4.3 抢占Swap 与 Recomputation连续调度引入一个新问题显存池被占满但还有高优先级请求想进来。vLLM 的策略是抢占preemption两种手段Swap把被抢占序列的 KV Cache 搬到 CPU 内存等显存释放再搬回来。缺点是 PCIe 带宽有限搬移本身耗时长序列 高并发时容易引发 swap 风暴。Recomputation不搬数据让被抢占序列从头或从 checkpoint重新计算。用重算开销换显存空间适合 CPU 内存也不宽裕的场景。生产上默认 swap但很多团队在长上下文场景会显式关闭 swap 改用 recompute避免 TTFT首 token 延迟被拖垮。五、生产调优把参数调对比换框架重要vLLM 上手成本很低但生产环境的差距全靠参数拉开。以下几个参数几乎决定了服务的吞吐上限参数默认值作用与调优建议--gpu-memory-utilization0.9控制 GPU 显存中留给 KV Cache 的比例余量留给计算图和碎片--max-num-seqs256单 batch 最大序列数直接决定并发上限--max-num-batched-tokens2048单步最多处理的 token 数影响 prefill 与 decode 的混合比例--block-size16逻辑块大小16 是吞吐与灵活性的平衡点--enable-prefix-cachingoff自动缓存重复前缀的 KV 块多轮对话/系统提示词场景收益显著--kv-cache-dtypeauto设为fp8后 KV Cache 显存直接减半E4M3部分模型支持实践中最值得投入的两个优化Prefix Caching多轮对话中system prompt 和历史轮次会反复参与 prefill。开启 prefix caching 后vLLM 按块哈希识别重复前缀、直接复用缓存块典型场景下 prefill 计算量下降 50% 以上。KV Cache 量化FP8 KV Cache 把显存占用直接减半对长上下文场景几乎是免费午餐。2026 年的 vLLM 已经把量化能力与 MLA 类模型结合长上下文成本被进一步压缩。六、总结与展望一句话概括 vLLM 的提速逻辑PagedAttention 解决显存不够用Continuous Batching 解决算力闲得慌两者叠加把 GPU 上每一字节显存、每一拍算力都推向饱和。论文数据是同等延迟下比 FasterTransformer/Orca 高 2-4 倍吞吐比 HuggingFace 高最高 24 倍、比 TGI 高最高 3.5 倍13。2026 年 3 月发布的 Model Runner V2则把这套思路从单机扩展到了多机多卡、MLA、流式请求等更复杂的场景4。对工程师来说最重要的是建立两个判断框架先算清 KV Cache 的账显存约束再想清楚调度粒度算力约束。这两件事想透了无论未来推理框架如何演进你都能快速评估任何一套系统的天花板。如果本文对你有帮助欢迎点赞收藏对 KV Cache 量化或调度策略有疑问欢迎评论区交流。Kwon et al., “Efficient Memory Management for Large Language Model Serving with PagedAttention”, OSDI 2023. https://arxiv.org/pdf/2309.06180.pdf ↩︎ ↩︎Yu et al., “Orca: A Distributed Serving System for Transformer-Based Generative Models”, OSDI 2022. https://www.usenix.org/conference/osdi22/presentation/yu ↩︎vLLM 官方博客中文“vLLM使用 PagedAttention 实现简单、快速且低成本的大模型服务”。https://blog.vllm.com.cn/2023/06/20/vllm.html ↩︎vLLM Blog, “Model Runner V2: A Modular and Faster Core for vLLM”, 2026. https://vllm-project.github.io/2026/03/24/mrv2.html ↩︎