导读:本期聚焦于辉辉创作的《PagedAttention原理是什么?vLLM如何用它解决大模型推理显存碎片问题》,敬请观看详情。操作系统用分页管理内存来避免碎片,大模型推理的显存占用却长期受限于连续内存分配。vLLM把这种思路搬到注意力机制上,提出PagedAttention。它把键值缓存切成分页块,像虚拟内存一样映射,使不同序列能共享和复用显存。传统推理框架为防碎片预留整块连续空间,导致利用率常低于四成。PagedAttention允许非连续存储,配合块表记录物理位置,显存浪费降到极低。本文从底层机制讲清它如何追踪每个请求的分页KV,怎样通过写时复制省去重复拷贝,以及相比连续缓存带来的吞吐提升。理解这套设计,才能明白为什么vLLM能在大批量并发下保持高显存效率。

在大型语言模型推理过程中,键值缓存(KV Cache)占据了大量显存,而传统推理框架往往要求这部分缓存以连续内存形式存在。当请求长度不一、并发量上升时,连续分配策略会产生严重的内部碎片和外部碎片,使得宝贵的GPU显存利用率常常跌至百分之四十以下。vLLM提出的PagedAttention,借鉴了操作系统的分页内存管理思想,将KV Cache划分为固定大小的块,通过块表完成逻辑到物理的映射,从而让显存使用变得灵活且紧凑。

PagedAttention原理是什么?vLLM如何用它解决大模型推理显存碎片问题

分页式KV缓存的底层设计

PagedAttention最核心的改变,是把原本必须连续存放的注意力键值对,拆成若干个大小固定的页面,一般称为block。每个block保存固定数量的token所对应的Key和Value张量。模型在自回归生成时,如果当前序列已写满一个block,就向内存管理器申请一个新的物理block,并在该序列对应的块表中追加映射项。这样一来,一个请求的KV Cache在物理显存上可以是不连续的,完全由块表来记录逻辑块编号与物理块编号的对应关系。

这种设计与传统方式形成鲜明对比。旧方案通常在序列开始前就按最大可能长度预分配一整段连续显存,无论实际生成多少token,预留部分都不能被别人使用。而PagedAttention只在需要时分配block,且block可被调度器在不同序列间灵活回收。下面的伪代码展示了块表的基本结构:

class BlockTable:
    def __init__(self):
        # 逻辑块到物理块编号的映射
        self.mapping = []

    def append_block(self, physical_id):
        self.mapping.append(physical_id)

    def get_physical(self, logical_id):
        return self.mapping[logical_id]

# 序列A的块表
table_a = BlockTable()
table_a.append_block(0)
table_a.append_block(3)
# 逻辑块1实际存在物理块3中
print(table_a.get_physical(1))

从实现角度看,分页机制还要求注意力计算内核能够接收非连续地址并正确读取。vLLM的CUDA内核会依据块表把各物理block中的KV拼成计算所需的完整序列视图,对上层算法而言序列仍是连续的,但底层显存完全离散。这种抽象隔离让显存管理效率和计算正确性同时得到满足。

写时复制与显存共享机制

在真实服务场景中,经常出现多个请求共享同一前缀的情况,例如系统提示词完全相同,或并行采样的多个输出来自同一上下文。传统框架会为每个请求复制一份前缀KV Cache,造成成倍显存消耗。PagedAttention引入了写时复制(Copy-on-Write)策略:初始时多个序列的块表指向同一个物理block,并将该block标记为只读;只有当某个序列需要修改其中内容时,才真正分配新block并拷贝数据。

这一机制极大提升了显存复用率。以下示例说明两个序列如何共享前缀块,又在写入时分裂:

# 序列A和B共享物理块0、1
table_a = BlockTable()
table_b = BlockTable()
for pid in [0, 1]:
    table_a.append_block(pid)
    table_b.append_block(pid)

# B要生成新token,需写入新逻辑块,触发复制
new_pid = alloc_block()
table_b.append_block(new_pid)
copy_from(src=1, dst=new_pid)
mark_readonly(1)

写时复制不仅省显存,也降低了启动延迟,因为共享前缀无需重复计算。在beam search等需要保留多候选路径的解码方法中,大量中间前缀都可被不同beam共享,PagedAttention使得这种共享成为默认行为而非额外优化。相比每次都完整克隆,显存占用可缩减数倍,尤其对长系统提示和批量采样价值明显。

相比连续缓存的吞吐与碎片对比

连续缓存方案由于预分配和长度对齐,内部碎片来自短请求占用长空间,外部碎片来自释放后留下的无法利用的小空洞。PagedAttention以固定block为最小单位,分配粒度更细,几乎消除了外部碎片;内部碎片仅限最后一个block未写满部分,比例由block大小决定,通常可控制在百分之十以内。实测中,同等并发下vLLM显存利用率可超过百分之九十。

高显存效率直接转化为更高吞吐。因为同样显存能容纳更多并发序列的KV Cache,GPU计算单元等待数据的空闲减少,请求排队时间缩短。我们可用一张简表对比两类方案:

维度连续缓存PagedAttention
分配方式按最大长度预分配连续段按需分block,非连续
碎片类型内外部均严重仅末块内部碎片
前缀共享需手动复制写时复制自动共享
典型显存利用率低于40%高于90%

当然,PagedAttention也带来一定实现复杂度,例如块表维护和异构内核改造。但其收益在大规模部署中远超成本。理解PagedAttention原理,有助于我们在自研推理系统或选型时,准确评估显存与并发的平衡点,也能更清晰地看懂vLLM为何成为高吞吐大模型服务的代表框架。

PagedAttentionvLLMLLM推理显存修改时间:2026-08-17 20:22:34

免责声明:​ 已尽一切努力确保本网站所含信息的准确性。网站内容多为原创整理与精心编撰,观点力求客观中立。本站旨在免费分享,内容仅供个人学习、研究或参考使用。若引用了第三方作品,版权归原作者所有。如内容涉及您的权益,请联系我们处理。
内容垂直聚焦
专注技术核心技术栏目,确保每篇文章深度聚焦于实用技能。从代码技巧到架构设计,为用户提供无干扰的纯技术知识沉淀,精准满足专业提升需求。
知识结构清晰
覆盖从开发到部署的全链路。AI、前端、编程、数据库、服务器、建站、系统层层递进,构建清晰学习路径,帮助用户系统化掌握开发与运维所需的核心技术。
深度技术解析
拒绝泛泛而谈,深入技术细节与实践难点。无论是数据库优化还是服务器配置,均结合真实场景与代码示例进行剖析,致力于提供可直接应用于工作的解决方案。
专业领域覆盖
精准对应开发生命周期。从前端界面到后端编程,从数据库操作到服务器运维,形成完整闭环,一站式满足全栈工程师和运维人员的技术需求。
即学即用高效
内容强调实操性,步骤清晰、代码完整。用户可根据教程直接复现和应用于自身项目,显著缩短从学习到实践的距离,快速解决开发中的具体问题。
持续更新保障
专注既定技术方向进行长期、稳定的内容输出。确保各栏目技术文章持续更新迭代,紧跟主流技术发展趋势,为用户提供经久不衰的学习价值。