news 2026/11/2 12:25:31

大模型推理加速三件套:量化、投机采样与PD分离实战解析

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
大模型推理加速三件套:量化、投机采样与PD分离实战解析

前两天我在一台消费级显卡上部署 Qwen 量化版跑推理,结果发现 INT4 模型居然只有 5 tokens/s,当时我第一反应是“这卡废了”。查了一圈之后才意识到,问题根本不在硬件,而在于推理引擎的调度方式和模型服务的负载特性。大模型推理加速里反复出现的“量化”“投机采样”“PD 分离”,其实分别对应着推理链路中最要命的三个瓶颈——带宽、串行生成和资源争抢。这篇文章我想把这三块内容讲透,连同我在 nano-vllm 上做实验的过程一起讲清楚,适合那些已经能跑通大模型、但对推理性能感到困惑,想系统理解加速原理的读者。

1. 先算清楚账:大模型推理到底慢在哪三处

想理解加速技术,第一步不是背概念,而是搞清楚推理为什么慢。很多优化方案看起来高大上,本质都指向同一个目标:用更少的资源、更快的时间,把一个 token 一个 token 地“挤”出来。

1.1 自回归生成机制让推理天然串行

大模型生成文本的核心机制是自回归:每生成一个 token,都要把当前已生成的全部 token 作为上下文,重新做一次前向计算,才能得到下一个 token 的概率分布。这个“生成下一个词依赖前面所有词”的循环,导致推理阶段无法像训练阶段那样大规模并行。

你可以把大模型想象成一个极其博学但极其啰嗦的教授,问它一个问题后,它必须先把之前写过的每个字都重新读一遍,然后才能写出下一个字。问题是这个“重读”的成本非常高——模型有多大,每次读一遍就要搬运多少数据。举个例子,一个 7B 参数的 FP16 模型,权重占 14GB 显存,每生成一个 token,都需要把全部 14GB 权重从显存搬到计算单元。按常见的 936GB/s 带宽算,光是搬运权重就需要 15ms 左右,理论极限也就是 60~70 token/s。实际跑起来往往只有一半甚至更低。

这个数据背后藏着一个反直觉的结论:推理阶段的计算单元大量时间在“等待数据”,而不是在做计算。大模型的单次前向乘法数量虽然不小,但相对于权重传输的时间来说,算力是过剩的。说白了,限制速度的是“运知识”的通道,而不是“用知识”的大脑。

1.2 三个瓶颈对应三条加速路线

我把推理慢这件事拆成三个独立的瓶颈来看,后面所有加速技术都是围绕它们展开的:

瓶颈现象对应加速技术核心思路
权重搬运带宽有限每个 token 都要读全量权重,显存带宽成为天花板量化减少权重和 KV Cache 的字节数,降低搬运量
自回归逐字串行每次只能生成一个 token,无法并行产出投机采样用小模型“先猜一段”,大模型一次性验证多个位置
Prefill 与 Decode 资源冲突长输入预处理和短输出生成互相抢 GPUPD 分离把两个阶段拆到不同机器/进程,各自独立优化

这三个方向不是互斥的,生产环境里经常叠加使用。但如果你不知道瓶颈在哪,随便乱开优化开关,不仅提不了速,反而可能拖慢系统。下面我从量化讲起,因为它最容易理解和上手。

2. 量化:把“运知识”的负担减到四分之一

量化是这三项技术里我最推荐先学的。它不仅直观,而且几乎适用于任何硬件场景,从手机到数据中心都能看到它的身影。

2.1 为什么量化对推理有奇效,但对训练帮助不大

量化的大意是把模型权重从高精度(FP16/BF16)压缩到低精度(INT8/INT4/FP8),比如原来一个权重用 2 字节存,压缩到 0.5 字节后,整个模型的体积就缩成四分之一。

关键问题是:为什么这个操作对推理提速这么明显,却很少听说有人用它加速训练?因为训练时你会一次性喂进去大批量的数据,计算强度很高,算力才是主要瓶颈;而推理时每生成一个 token 只做一次不完整的前向计算,计算强度极低,系统始终被“搬运数据”卡着脖子。量化把每次搬运的数据量直接砍掉 75%,自然就能撬动好几倍的速度提升。

拿同一个 7B 模型举例,FP16 时每 token 要搬 14GB 数据;压成 INT4 后只要 3.5GB,理论上生成极限能从 60 token/s 提到 260 token/s 左右。虽然实际同时还有 KV Cache 读取、激活值计算和内核调度开销,速度不可能完全线性翻倍,但体感提升绝对明显。这也是为什么社区里许多人跑 27B 或 30B 级别大模型时,都会优先选 4-bit 量化版本——本质就是用精度换带宽,而且大多数场景下这波交易相当划算。

2.2 主流量化方案对比:GPTQ、AWQ、GGUF、MLX

量化不是简单地把 FP16 四舍五入成 INT4,不同方案对精度损失的把控、适用的推理引擎、部署场景差别很大。我用一个表总结一下目前常见的路径:

方案压缩思路典型使用场景配套引擎/工具特点
GPTQ基于二阶梯度信息校准,按层量化到 INT4/INT3数据中心 GPU 部署vLLM、AutoGPTQ、ExLlamaGPU 推理成熟,吞吐高
AWQ根据激活值大小保护显著通道,减少量化损失GPU 部署,需要更好质量vLLM、AutoAWQ对激活值敏感场景更稳
GGUF支持混合精度(Q2_K、Q4_K_M 等)和 CPU/GPU 混合推理本地个人电脑、低显存环境llama.cpp、OllamaCPU 友好,生态模型最多
MLXApple Silicon 原生精度优化,支持 4-bit/8-bitMacBook、Mac mini 本地部署MLX 社区推理内存带宽利用充分,省电

选型时我的经验是三个问题定方向:你跑在什么硬件上?显存够不够装下 FP16 权重?你对精度损失敏感吗?如果是本地个人电脑且有 NVIDIA 显卡,优先考虑 GGUF 搭配 Ollama;如果是 API 服务、追求高吞吐,GPTQ 或 AWQ 走 vLLM 会更合适;如果手里是 Mac,别犹豫,直接用 MLX。

值得多说一句的是,量化社区现在也在分化:有些量化版本做得好,校准数据集覆盖广,几乎无损;有些只是简单转格式,跑复杂任务时明显变蠢。qwen3.8-27b这类热门模型的 4-bit 版本我试过几个,不同发布者做出来的效果差异很大,后面我会专门讲怎么避坑。

2.3 量化部署实操:从下载模型到跑起来的一次完整记录

以 GGUF 格式为例,我挑一个最典型的消费级部署链路,整条跑下来大概十分钟。

第一步,去 Hugging Face 或 ModelScope 上下载目标模型的 GGUF 量化版,注意文件名里的量化等级标识。Q4_K_M 是平衡之选,显存宽裕想保精度可以用 Q5_K_M,显存很紧就用 Q3_K_M 或 Q2_K。下载文件名里那个-q4_k_m.gguf后缀千万别看漏了,很多人栽在这。

第二步,用 llama.cpp 或 Ollama 直接加载。Ollama 更简单,写好一个Modelfile指向本地 GGUF 文件就能用;想折腾底层可以手动编译 llama.cpp,跑命令时加-ngl参数把层全部放进 GPU:

# llama.cpp 加载 Q4_K_M 量化模型,全部层放 GPU ./llama-cli -m ./models/qwen3-27b-q4_k_m.gguf -ngl 99 -c 8192 -f prompt.txt

第三步,算一下显存是否够用。以 27B 模型 INT4 为例,权重约 17GB,8K 上下文的 KV Cache 大约 1~3GB,加上激活值和其他开销,24GB 显存的卡会卡在危险边缘;如果用 Q3 量化把权重压到 13~14GB,就能稳定塞进去。这也是为什么很多人用 27B 模型跑 4-bit 在单卡上磕磕碰碰——不是模型不行,是没算清楚 KV Cache 的账。

如果你的场景是 GPU 单机高并发,也可以走 GPTQ + vLLM 路线,加载起来同样透明:

# 伪代码示例:vLLM 加载 GPTQ 量化模型 from vllm import LLM llm = LLM( model="Qwen/Qwen3-7B-GPTQ-Int4", quantization="gptq", max_model_len=8192, )

2.4 量化最容易翻车的三个地方

第一,校准数据集决定了量化模型的“智力下限”。GPTQ/AWQ 这类方案需要一组代表真实分布的文本做校准,如果发布者用的是和模型领域差距很大的数据,量化后的模型在专业任务上会明显退步。所以下载量化版尽量选官方发布的,或者社区口口相传、任务表现比自己转的好得多的版本。

第二,量化模型不是越大越好,也不是越小越强。对于 3B、7B 这类小模型,INT4 量化带来的精度损失会更明显,因为模型本身的冗余度低;而对 70B 级别的大模型,4-bit 量化损失往往可以忽略。这也是为什么我的建议是:大模型放心量化,小模型慎重量化。

第三,显存占用降了,推理不一定自动变快。有些量化实现的反量化(dequant)过程本身也有开销,特别是不支持低精度矩阵乘法的硬件上,实际收益会大打折扣。判断一个量化版好不好,不能只看“能不能跑”,还要看实测生成的 tokens/s。如果量化后速度没提升,试试换成 AWQ 或换推理引擎,很可能模型格式和引擎适配出了问题。

量化解决了“每次读太重”的问题,但还有一个待解难题:即使权重变轻了,自回归依然是逐字进行的。你每生成一个 token,都得等上一次完整前向结束。下面这个技术,专门从这个角度下手。

3. 投机采样:与其一个字一个字等,不如“先猜后验”

投机采样(Speculative Decoding)是我个人觉得大模型推理加速里最有意思的一个想法。它不改变模型本身,也不用降精度,而是改变了生成策略——让一个“快但不太聪明”的小模型打草稿,再让“慢但聪明”的大模型一次性验证一整段草稿。

3.1 先搞懂验证为什么比生成便宜

这背后的关键点在于并行度。大模型前向计算时,如果只输入一个 token,它只能输出一个 token;但如果一次输入一串 token(比如 5 个),它可以并行预测这 5 个位置各自的下一个 token——这次前向的计算量和输入长度成正比,但耗时不会同步增长,因为 GPU 本身就擅长并行矩阵运算。

所以投机采样的玩法是:先用一个小得多的草稿模型(Draft Model)快速生成 K 个候选 token,然后把这一段候选全部喂给大模型做一次并行验证。大模型会对每个位置给出自己的概率分布,如果草稿 token 落在接受范围内,就直接通过;如果某个位置被拒绝,就从这个位置重新开始生成,丢弃后面所有草稿。

你可以把它类比成工作场景中的“秘书先起草,领导一次性审阅”。如果每次草稿质量都很高,领导看一眼就能签完全文;如果草稿写得很烂,领导还得坐下来重写,反而浪费时间。从期望上看,只要草稿够好,一次大模型前向就能同时完成多个 token 的生成,推理速度就这样提上来了。

理论上,如果草稿长度 K=5、平均接受率 r=0.8,那么每次大模型验证平均能产出 (1 - r^(K+1)) / (1 - r) 约 3.3 个 token,潜在加速接近 3 倍。当然,实际还要扣除草稿模型本身的前向开销,通常体感是 1.5~2.5 倍,但已经很可观了。

3.2 草稿模型不是越强越好:选型要看“性价比”

投机采样的效果高度依赖草稿模型的选择。说白了,要找一个“猜得中率中肯、跑得足够快”的小模型,而不是随便拿个大模型当草稿。

草稿模型太弱,接受率低,多一次的快速预测变成了纯额外开销;草稿模型太强,比如直接拿一个 7B 模型给 27B 模型当草稿,它自己的生成时间就占了很大比重,省下的验证时间全赔进去。常见做法是选择同系列、同 tokenizer 的较小尺寸模型,比如主模型是 Qwen3-27B,草稿模型用 Qwen3-0.6B 或 1.7B。

这里有一个特别容易踩的坑:草稿模型和目标模型的 tokenizer 必须完全一致。如果 tokenizer 不同,草稿输出的 token 序列在大模型眼里根本不是一句话,投机采样直接失效。另外,草稿生成的 temperature 和顶部采样的参数最好和目标模型匹配,否则接受率会打折。

3.3 vLLM 环境下的投机采样配置参考

在 vLLM 里开启投机采样非常简单,核心参数就两个:speculative_model指定草稿模型,num_speculative_tokens指定草稿长度。官方建议通常在 3~5 之间,太小加速有限,太大草稿模型延迟尾随严重。

from vllm import LLM llm = LLM( model="Qwen/Qwen3-27B-BF16", speculative_model="Qwen/Qwen3-0.6B", num_speculative_tokens=5, )

跑在线服务时也一样,用 OpenAI 兼容的启动参数即可:

vllm serve Qwen/Qwen3-27B-BF16 \ --speculative-model Qwen/Qwen3-0.6B \ --num-speculative-tokens 5

启动后建议盯着服务日志里的acceptance rate指标。如果你看到接受率稳定在 0.4 以下,说明草稿模型选得太弱,换大一档试试;如果 tokens/s 反而下降了,则说明草稿模型太快了、但这也可能意味着草稿长度太长,把它调小几档对比一下。投机采样的调参本质就是一个“草稿收益减去草稿成本”的平衡问题。

值得注意的是,规模较小的本地模型做起投机采样来比较吃亏——草稿模型的额外开销会吃掉大部分收益。我实测下来,主模型至少 14B 级别以上,开启投机采样才有明显正收益;7B 以下开它真的属于“折腾自己”。

量化把权重搬得更轻了,投机采样把串行生成改成了并行验证,接下来还剩一个工程层面的大问题:在线服务里,很多请求在“读题”阶段和“答题”阶段会互相打架,这就是 PD 分离登场的理由。

4. PD 分离:给 Prefill 和 Decode 各开一条生产线

PD 分离全称是 Prefill-Decode Disaggregation,翻译过来就是“预填充与解码分离”。在阅读代码或者看部署方案时,你可能会看到 “Prefill” 和 “Decode” 这两个词,它们分别指代推理过程中两个性质截然不同的阶段。

4.1 Prefill 和 Decode 是性格完全不同的两种负载

Prefill(预填充)阶段:用户输入的 prompt 被一次性喂给模型,做并行计算,生成第一个 token 的同时产出所有层的 KV Cache。这个阶段计算量大、耗时与输入长度成正比,GPU 的利用率很高。

Decode(解码)阶段:从第一个 token 开始,每轮只输入上一个 token,逐步生成后续 token。这个阶段计算量小,主要受显存带宽限制,并且因为不同请求进度不一,需要不断调度批处理。

从算力视角看,它们俩几乎是两个方向的负载——一个算力饥渴,一个带宽饥渴;一个吃满 GPU 计算核心,一个闲着计算核心等数据。如果把它们塞在同一张卡上,典型的灾难场景是:某个用户发来一篇超长文档,Prefill 阶段瞬间把 GPU 占满,后面所有正在做 Decode 的在线请求全部被拖慢;而 Prefill 跑完以后,轮到 Decode 了,GPU 的计算核心又大把闲着。

维度PrefillDecode
输入特征一次处理全部 prompt token每次只处理一个 token
计算特征计算密集型访存密集型
耗时与 prompt 长度强相关与生成长度强相关
批处理弹性差,长 prompt 会独占资源好,可大量并发批处理
优化侧重矩阵算力、KV Cache 预建带宽利用、连续批处理调度

4.2 分离部署后发生了什么

PD 分离的思路很直接:不把这两个阶段放在同一块 GPU 上,而是分别部署专门的 Prefill 实例和 Decode 实例。请求进来后,先由负载均衡器分给某个 Prefill 节点,完成第一次前向和 KV Cache 构建;随后把 KV Cache 从 Prefill 节点传给 Decode 节点,Decode 节点根据这份 Cache 持续生成 token。

这样做的好处在于三层:

  1. 互不抢资源。长文档读题再也不会拖垮正在生成的请求,反之亦然。
  2. 可以独立缩放。如果在线请求普遍是短 prompt 长输出,就多扩 Decode 节点;如果是 Agent 场景大量长上下文,就多扩 Prefill 节点。
  3. 各阶段用不同优化。Prefill 节点可以选用更高算力的卡(比如 A100/H100),Decode 节点可以选用带宽高、性价比合适的卡。不同规格的硬件各司其职,整体单位成本反而下来了。

当然,工程实现不是嘴上说的这么简单。KV Cache 动辄几百 MB,从 Prefill 实例传到 Decode 实例这个动作本身也有延迟;集群里如果刚好没有空闲 Decode 实例,请求还得排队。所以生产环境下通常配合请求调度器做全局视角的流量分发,把 Prefill 和 Decode 的负载预测也纳入规划。

对于单机用户来说,PD 分离听起来有点遥远,但这里有一个共享同一个内核思想的“轻量版”优化:Chunked Prefill(分块预填充)。它把长 prompt 切成若干 chunk,每处理完一个 chunk 就去服务一批 Decode 请求,再回来处理下一个 chunk,相当于在单卡内部给 Prefill 和 Decode 做了时间片轮转,能显著缓解长上下文请求阻塞在线回答的问题。如果你跑的是 vLLM 这类引擎,也能直接体验这个思路。

5. 从原理到上手:怎么用 nano-vllm 把这些技术串起来

讲到这儿,量化、投机采样、PD 分离的理论部分都过了一遍。但是纸上得来终觉浅,真正理解这些机制,还是要在代码和实验里摸一把。我自己学习时用的是 nano-vllm,一个刻意保持精简的推理引擎实现,非常适合用来搞懂大模型推理的关键功能。

5.1 为什么建议用 nano-vllm 当学习入口

vLLM 本身功能全面,但代码量大,调度、分页、内存管理、模型加载、采样器全混在一起,新手看代码特别容易迷失。nano-vllm 的设计目标就是“小而全”——保留 vLLM 的核心机制,比如 PagedAttention(分页注意力)、Continuous Batching(连续批处理)、投机采样、量化加载等,但剥离了大量生产级细节,代码量小很多。

我建议的学习路径是这样的:先读调度器(Scheduler),看它如何管理请求状态;再读分页 KV Cache 管理器,理解显存块分配逻辑;接着看模型 worker 和采样器,弄懂量子化和投机采样在哪里接入;最后对照一个请求的完整生命周期,把 Prefill、Decode 的切换过程在代码里标记出来。

5.2 一套可复现的本地推理加速实验

我在一张 24GB 显卡上做过一组对比实验,实验对象是 Qwen3-4B 基础版与 INT4 量化版,同时记录开启投机采样前后的吞吐数据。这个规模不大,适合复现。

第一步,用uv或conda建一个干净环境,安装 nano-vllm 以及依赖。第二步,分别以 FP16、INT4、INT4+投机采样三种配置启动服务,执行同一组测试 prompt,记录 tokens/s 和首 token 延迟。第三步,把--enable-prefix-caching或 chunked prefill 开关打开再试一轮,观察长 prompt 对短请求的干扰是否下降。

启动命令大致长这样:

# 开启投机采样的 nano-vllm 服务示例 python -m nano_vllm.serve \ --model Qwen/Qwen3-4B \ --dtype float16 \ --speculative-model Qwen/Qwen3-0.6B \ --num-speculative-tokens 4 \ --max-model-len 8192

实验记录表对一个参考,方便对比不同配置的收益:

配置权重体积实测吞吐(约)首 token 延迟备注
FP16 基线~8GB低正常对照样本
INT4 量化~2.5GB明显提升下降带宽瓶颈缓解
INT4+投机采样~2.5GB进一步提升略增需要接受率正常
INT4+分块 Prefill~2.5GB稳定长 prompt 干扰降低并发场景更稳

当然,具体的数字会因显卡型号和驱动差异而不同,但结论趋势是一致的:量化带来的收益几乎最大,投机采样在模型较大时才显著,分块 Prefill 对在线并发更有价值。

5.3 不同硬件条件下怎么组合这三项技术

结合我自己踩过的坑,给几个不同硬件规模下的组合参考:

  • 16GB 消费级显卡:优先跑 INT4/GGUF 量化模型,先保证能装下。投机采样收益有限,但如果主模型在 14B 以上可以尝试;PD 分离不用想。
  • 24GB 消费级显卡:量化是必须的,27B 模型 Q4 可以流畅跑;投机采样搭配 0.6B 或 1.7B 草稿模型,能在量化基础上再提速 20%~50%。如果你是 API 服务或处理长文档,考虑开 chunked prefill。
  • 多卡/数据中心 GPU:量化、投机采样、PD 分离可以全上。生产环境通常还会配合前缀缓存、路由策略,让 Prefill 和 Decode 实例各自扩容。此时不光是推理引擎的调参问题,还有分布式 KV 传输和负载预测的全局设计。
  • Apple Silicon 设备:优先 MLX 格式量化,投机采样在部分实现里也可以开,但由于 Mac 的内存带宽相对较大,收益不如 NVIDIA 平台明显。

最后说一点我个人的真实体会。学习这三项技术时,最容易犯的错误是“一上来全开”。我见过不少人十八般武艺全部加在同一套服务上,最后没快多少,反而增加了调度延迟和排错难度。从量化开始,确认瓶颈逐步释放后,再加投机采样;PD 分离属于架构级的改动,适合你对前两项的收益边界有清晰认知以后再考虑。如果你也在研究大模型推理加速,建议先从这篇提到的三个底层瓶颈入手,对照自己的部署环境一项一项测,比盲目堆参数有效得多。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/11/2 12:24:47

大模型算子框架选型:Triton、torch.compile与CUDA C++实战决策指南

1. 项目概述:为什么“大模型算子框架选型”不是技术选型,而是工程决策分水岭 你手头刚跑通一个7B参数的LLM微调任务,训练loss曲线漂亮得像教科书插图,但一到推理阶段——batch_size1时延迟280ms,batch_size4直接OOM&am…

作者头像 李华
网站建设 2026/11/2 12:23:43

Node.js安全攻防:CTFSHOW Web334-344题解与漏洞分析

1. Node.js安全攻防实战:CTFSHOW Web334-344题解全析在网络安全竞赛中,Node.js因其独特的运行机制和丰富的模块系统,成为CTF比赛中高频出现的考点。本系列将深入解析CTFSHOW平台Node.js方向的11道典型题目(Web334-344)…

作者头像 李华
网站建设 2026/11/2 12:23:43

风力发电机组振动监测:边缘计算与DSP频谱分析实践

简介:面向风力发电机组运维与故障诊断需求,这份PDF文献围绕齿轮箱、轴系等关键部件的振动信号监测展开,梳理嵌入式微处理器就地分析、远程在线监控及视频音频辅助监控的系统方案,适合风电运维人员、测控与电气类专业师生参考。资源…

作者头像 李华
网站建设 2026/11/2 12:23:41

低功耗蓝牙(BLE)能耗仿真技术与优化实践

1. 蓝牙网络能耗仿真概述 在物联网设备爆发式增长的今天,低功耗蓝牙(BLE)技术凭借其优异的能耗表现,已成为可穿戴设备、智能家居等场景的首选无线通信方案。作为一名长期从事无线网络仿真的工程师,我深刻理解能耗仿真对于BLE设备开发的关键价…

作者头像 李华
网站建设 2026/11/2 12:23:32

Codex跨系统小工具开发:解决路径、编码、换行与依赖的复现难题

1. 跨系统小工具为什么总在“能跑”和“结果对”之间翻车用 Codex 这类 AI 编程助手写跨系统小工具,最让人抓狂的不是它写不出代码,而是它写出来的代码在你这台机器上跑得挺欢,换一台机器、换一个系统、换一个目录,结果就悄悄变了…

作者头像 李华
网站建设 2026/11/2 12:23:00

从AI每日简报看开发栈演进:Mojo、Vulkan与Win11实战

1. 每日AI行业简报的定位与信息筛选逻辑每天早上花十五分钟翻一遍AI行业简报,这个习惯我坚持了快两年。2026年9月25日这一期的内容密度尤其高,几个热搜词凑在一起——AI、Mojo、Win11、Python、Vulkan——表面看是五条不相干的线索,实际上串起…

作者头像 李华