← 返回目录 模块 4 / 8

4.1 模型并行策略(Model Parallelism)

分布式

模型并行(Model Parallelism)是指将一个大语言模型拆分到多个 GPU 上协同推理的技术集合。随着模型规模从 7B 增长到 405B 甚至 671B(如 DeepSeek-V3),单 GPU 显存(即使 H100 的 80GB)远不足以容纳完整模型参数 + KV Cache + 中间激活值。模型并行通过将模型的不同部分分布到多个 GPU,突破了单卡显存墙,同时通过并行计算降低推理延迟。

模型并行主要分为四种基本策略:

  • Tensor Parallelism(TP,张量并行):在层内切分权重矩阵
  • Pipeline Parallelism(PP,流水线并行):在层间切分
  • Data Parallelism(DP,数据并行):在请求级别并行
  • Expert Parallelism(EP,专家并行):专为 MoE 模型的 expert 分布设计

在实际部署中,这些策略通常组合使用以最大化硬件利用率。

Tensor Parallelism(TP)

TP 是 Megatron-LM 提出的层内切分策略,将每个 Transformer 层的权重矩阵沿特定维度切分到多个 GPU。在 Transformer 中,TP 主要应用于 MLP 层(gate_up_proj, down_proj)和 Attention 层(qkv_proj, o_proj)。

列切分(Column Parallel):对于线性层 Y = X * W,其中 W 形状为 [in_features, out_features],列切分将 W 沿输出维度切分为 W = [W_1, W_2, ..., W_k],每个 GPU 保存 W_i 形状为 [in_features, out_features/k]:

Y_i = X * W_i # 每个 GPU 独立计算
Y = [Y_1, ..., Y_k] # 输出维度拼接

行切分(Row Parallel):将 W 沿输入维度切分为 W = [W_1; W_2; ...; W_k](纵向堆叠),上一层的列切分输出直接作为本层输入:

Y_i = X_i * W_i # X_i 是上层的列切分输出
Y = Y_1 + ... + Y_k # All-reduce 求和

通信量分析:行切分层需要 All-reduce 通信,通信数据量为 batch_size * seq_len * out_features * dtype_size。All-reduce 的通信复杂度为 2(k-1)/k * data_size(k 为 TP size)。在单机 NVLink 环境下(A100: 600 GB/s,H100: 900 GB/s),此开销很小。例如 LLaMA-70B decode 阶段单次 All-reduce 约 32 KB,传输时间约 0.05 μs。但在跨节点场景下(InfiniBand 12.5-50 GB/s),TP 通信开销显著增加,因此 TP 通常限制在单节点内。

vLLM 的 TP 实现继承自 Megatron-LM 的 parallel_state.py,通过 initialize_model_parallel 函数构建 TP 组。vLLM 扩展了多种 All-reduce 后端:Custom AllReduce(NVLink 优化)、FlashInfer AllReduce、PyNcclCommunicator(NCCL)、SymmMemCommunicator(PyTorch symmetric memory)。

Pipeline Parallelism(PP)

PP 将模型的不同层分配到不同 GPU。例如 80 层的模型,PP size = 4,则每个 GPU 负责 20 层。

PP 的核心问题是流水线气泡(Pipeline Bubble)。在 1F1B(One-Forward-One-Backward)调度下,气泡比例公式为:

Bubble ratio = (p - 1) / (m + p - 1)

其中 p = PP size,m = micro-batch 数量。在推理场景中没有反向传播,气泡问题显著简化,可以通过 interleaved scheduling 和 continuous batching 缓解。PP 的通信模式为 P2P(Point-to-Point),通过 send_tensor_dict / recv_tensor_dict 实现。

vLLM 中 PP 组的构建位于 parallel_state.py(第 1635-1651 行),通过 transpose(2, 4) 交换 PP 和 TP 维度,保证 PP 组跨 TP 组正交:

group_ranks = (
    all_ranks.transpose(2, 4).reshape(-1, pipeline_model_parallel_size).unbind(0)
)

例如 8 GPU, TP=2, PP=4:

  • TP 组:[0,1], [2,3], [4,5], [6,7]
  • PP 组:[0,2,4,6], [1,3,5,7]

Data Parallelism(DP)

DP 将完整的模型副本部署到多组 GPU,每组独立处理不同请求。推理时 DP 没有梯度同步需求,几乎可以线性扩展吞吐量:

维度训练时 DP推理时 DP
同步需求每步 All-reduce 梯度无需同步
负载均衡数据分片固定需要请求路由
通信量大(梯度大小 ≈ 模型大小)极小
扩展性受梯度同步限制近乎线性扩展(0.85-0.95 * d)

DP 的挑战在于前缀缓存的局部性——每个副本有独立 KV Cache。解决方案包括粘性路由(同一前缀路由到同一副本)和全局 KV 缓存(LMCache 跨副本共享)。

Expert Parallelism(EP)

EP 专为 MoE 模型设计,将不同 expert 分配到不同 GPU。MoE 层的计算流程为 Router -> All-to-all Dispatch -> Expert Compute -> All-to-all Combine。通信模式为 All-to-all,通信量约为 B * S * H * top_k * 2(dispatch + combine)。

vLLM 支持多种 All-to-all 后端:

  • DeepEP:DeepSeek 开源的高效 all-to-all 库
  • FlashInfer:NVLink 优化的 two-sided/one-sided 通信
  • NIXL:基于 UCX 的统一通信层

组合策略:3D Parallelism

3D Parallelism = Data Parallelism * Tensor Parallelism * Pipeline Parallelism

典型部署配置(LLaMA3-405B):

  • TP = 8(单节点内,利用 NVLink)
  • PP = 8(跨 8 个节点)
  • DP = 多副本(请求级并行)
  • 总 GPU = 64+
策略切分维度通信模式通信量最佳适用场景
TP层内权重All-reduce高(需 NVLink)单节点多卡,大模型单层放不下
PP层间P2P中等(激活值)跨节点,减少单卡层数
DP请求级几乎无无/极小高吞吐在线服务
EPMoE expertAll-to-all中高(token dispatch)MoE 模型(DeepSeek-V3 等)

应用场景

  • TP:所有超过单卡显存的模型都必须使用。70B 模型至少 TP=2(FP16 约 140GB),405B 至少 TP=8。TP 是 vLLM 中最常使用的并行策略。
  • PP:当 TP 受限时(如 TP size 不能超过单节点 GPU 数),PP 用于进一步降低单卡负载。DeepSeek-V3 的 671B 模型部署中使用了 PP 跨节点切分。
  • DP:在线 API 服务中提升吞吐量的首选手段,结合负载均衡器实现水平扩展。
  • EP:MoE 模型必选策略。DeepSeek-V3 在 96 H100 上 EP=24, DP=4。

与其他概念的关系

模型并行策略直接决定 KV Cache 的分布方式。TP 下 KV Cache 被切分到同组各卡;PP 下每卡持有不同层的 KV Cache;DP 下每副本有独立 KV Cache。Disaggregated Serving(分离式推理)进一步将 TP/PP 的分布式环境扩展到跨节点的 Prefill-Decode 分离。Quantization 可以降低单卡内存压力,从而减少所需的并行度。

4.2 Disaggregated Serving(分离式推理)

架构

Disaggregated Serving(分离式推理)将 LLM 推理的 Prefill 和 Decode 两个阶段分配到不同的 GPU 集群上独立执行。Prefill Cluster(P 集群)负责处理 prompt 计算和 KV Cache 生成,Decode Cluster(D 集群)负责自回归 token 生成。两阶段之间通过高速网络传输 KV Cache。

为什么需要分离

LLM 推理的两个阶段存在根本性的资源需求矛盾:

  • Prefill 阶段(Compute-bound):一次性处理整个 prompt 的所有 token,需要大量矩阵乘法,GPU 计算单元利用率高。瓶颈是 GPU 算力。
  • Decode 阶段(Memory-bound):每次只处理一个 token,主要开销在于从 HBM 读取 KV Cache。瓶颈是内存带宽。

当两者混合在同一 GPU 上时,Prefill 会抢占 Decode 的计算资源,导致 decode token 的 ITL(Inter-Token Latency)剧烈波动;同时 Decode 的 KV Cache 占用大量显存,限制了 Prefill 可以处理的 batch size。

架构设计

分离式推理架构包含三个核心组件:

  1. Prefill Pool:一组 GPU 专用于 prompt 处理和 KV Cache 计算。P 集群采用大 batch、高算力策略,最大化 TTFT(Time To First Token)的吞吐量。
  2. Decode Pool:一组 GPU 专用于自回归生成。D 集群采用小 batch、低延迟策略,保证 ITL 稳定。
  3. KV Cache 传输通道:P 集群计算完成后,将 KV Cache 通过高速网络传输到 D 集群。这是一个关键瓶颈。

KV Cache 传输挑战

KV Cache 体积极为庞大。对于 LLaMA3-70B(80 层,8 KV head,head_dim=128),每 token 的 KV Cache 大小约为 2 * 80 * 8 * 128 * 2 (FP16) = 327,680 bytes ≈ 320 KB。4K context 约 1.28 GB,128K context 约 40 GB。即使 400 Gbps InfiniBand,传输 1GB 也需要约 20ms。

传输协议实现

vLLM 在 vllm/distributed/kv_transfer/kv_connector/ 中实现了多种 KV 传输连接器:

  • MooncakeConnector:基于 Mooncake Transfer Engine,使用 RDMA(InfiniBand/RoCE)或 TCP。支持 P-push 模式(Prefill 主动推送)和异步发送。支持 P 和 D 使用不同 TP size。
  • NIXLConnector:基于 NVIDIA 的统一通信库 NIXL(基于 UCX)。支持零拷贝传输(KV cache block 注册为 NIXL descriptors),UCX 自动选择最优传输路径(NVLink > InfiniBand > PCIe > TCP),支持异构布局(不同 block size、layout、TP size)。
  • LMCacheConnectorV1:基于 LMCache 项目,提供跨引擎 KV cache 共享和多级 offloading(GPU HBM -> 主机内存 -> SSD -> 远程缓存)。支持事件驱动的缓存发现和 Layer-wise 异步传输。
# Mooncake Worker 初始化
class MooncakeConnectorWorker:
    def __init__(self, vllm_config, engine_id, kv_cache_config):
        self.engine = TransferEngine()  # Mooncake C++ 引擎
        self.engine.initialize(self.hostname, "P2PHANDSHAKE", protocol, "")
        # protocol: "rdma" 或 "tcp"

延迟节省分析

指标混合部署分离部署说明
TTFT中等更低P-cluster 专精大 batch prefill,算力利用率高
ITL高(波动大)更低(稳定)D-cluster 不受 prefill 抢占
吞吐量受限于混合调度更高P 和 D 分别优化各自 batching
KV 传输开销无增加需要额外的网络传输时间

关键权衡:短上下文(< 4K)时 KV 传输开销可能超过分离收益;长上下文(> 4K)时分离收益显著。

相关论文

  • Splitwise(USENIX ATC 2024):将 prefill 和 decode 分离到不同机器,提出 chunked prefill 平滑负载和 KV cache 复用策略,多个 decode worker 可共享同一 prefill worker 的 KV cache。
  • DistServe(OSDI 2024):将 goodput(满足 SLO 的请求比例)作为优化目标。发现混合部署时 prefill 对 decode 干扰导致大量请求违反延迟 SLO,分离后 goodput 提升 1.5-2.5x。P 和 D 使用独立 batching 策略。

应用场景

  • 长上下文推理服务(8K+ 上下文),如文档分析、代码库理解
  • 对 ITL 稳定性要求高的实时对话系统(chatbot API)
  • 高吞吐的 Prefill 批处理场景(RAG 系统批量处理大量 prompt)
  • 需要差异化硬件配置的场景(P 集群用 H100,D 集群用 A100 降低成本)

与其他概念的关系

Disaggregated Serving 是模型并行策略(TP/PP/DP)的上层扩展——它不是在单次推理中并行,而是在系统架构层面分离计算阶段。它依赖于 KV Cache 管理(PagedAttention、Prefix Caching)来处理跨节点的缓存传输。LMCache 是 Disaggregated Serving 的关键基础设施,提供多级 KV Cache 存储和共享。Quantization 通过减少每 token KV Cache 大小,可以降低 KV 传输的带宽压力。

4.3 量化(Quantization)

优化

量化(Quantization)是将浮点数模型参数、激活值或 KV Cache 以低位宽整数或低精度浮点数表示的技术。核心思想是将连续的值域映射到离散的整数格点上,从而大幅降低模型的内存占用、带宽需求和计算能耗。在 LLM 推理中,量化直接决定了单 GPU 能否容纳更大的模型,以及推理吞吐量的上限。

量化的数学基础

最基础的对称线性量化将浮点张量 x 映射到整数 q:

scale = max(|x|) / (2^(b-1) - 1) # b = 位宽
q = round(x / scale)
x_approx = q * scale # 反量化

其中 scale 是缩放因子,(2^(b-1) - 1) 是量化范围的最大值(如 INT8 为 127)。非对称量化增加 zero_point 偏移量来处理非对称分布:

scale = (max - min) / (2^b - 1)
zero_point = round(-min / scale)
q = round(x / scale + zero_point)

FP8(E4M3 / E5M2)

NVIDIA Hopper 架构引入了两种 8-bit 浮点格式:

  • E4M3:1 符号位 + 4 指数位 + 3 尾数位,范围约 0.00195 到 448,主要用于 weights 和 activations
  • E5M2:1 符号位 + 5 指数位 + 2 尾数位,范围约 0.000061 到 57344,主要用于 gradients

FP8 计算需要 Hopper GPU(H100/H200)的 Tensor Core 支持。vLLM 中通过 torch._scaled_mm 和 float8_e4m3fn dtype 实现。FP8 相比 FP16 将存储减半(每 token 的 KV Cache 从 2 字节降至 1 字节),同时 Hopper 的 FP8 Tensor Core 提供 2 倍于 FP16 的峰值算力。

INT8 / INT4

INT8:对称量化 scale = max(|x|) / 127, q = round(x / scale)。INT8 矩阵乘法利用 NVIDIA INT8 Tensor Core,峰值算力是 FP16 的 2 倍。量化粒度分为:

  • Per-tensor:整个张量共享一个 scale,最简单但精度损失最大
  • Per-channel:每个输出通道独立 scale,常见于权重量化
  • Per-group:每 32/64/128 个元素一组共享 scale,精度最好但存储 overhead 增加

INT4:将每 16 个 FP16 weights 压缩到 4 bits,加上 group-wise scale/zero_point。存储压缩比 4:1,但计算时需要反量化到 FP16/INT8。主要用于权重存储压缩。

AWQ(Activation-aware Weight Quantization)

AWQ 的核心洞察:不是所有权重通道都同等重要。通过观察 activations,可以发现某些通道对输出影响更大(salient channels)。AWQ 通过 per-channel scaling 保护这些重要通道:

min_s E[ || X * (W - quant(W * s) / s) ||^2 ]

其中 s 是逐通道缩放因子,通过少量校准数据优化得到。对于 salient channels(激活值幅值大的通道),使用较大的 s 值减小其相对量化误差。AWQ 通常支持 INT4/INT3/INT8,精度在同等比特率下通常优于 GPTQ。vLLM 通过 vllm/model_executor/layers/quantization/awq.py 支持 AWQ 模型加载。

GPTQ(Gradient-based Post-training Quantization)

GPTQ 是一种逐层的后训练量化方法,利用 Hessian 矩阵 信息补偿量化误差。源自 OBQ(Optimal Brain Quantization):

对于某层权重 W,量化引入误差 ΔW = W - W_q
对损失函数的二阶影响: ΔL ≈ ΔW^T * H * ΔW,其中 H = E[X^T X]

GPTQ 使用 Cholesky 分解稳定 Hessian 逆的计算、采用任意顺序量化配合批处理更新加速、支持 group-wise quantization(默认 128 个权重一组共享 scale)。校准数据通常需要 128-256 条。

# GPTQ 逐层量化流程(示意)
for each layer:
    H = X^T @ X              # 计算 Hessian
    H_inv = cholesky_inverse(H)  # Cholesky 分解求逆
    for each weight group:
        w_q = round(W[group] / scale)
        error = W[group] - w_q * scale
        # 用 Hessian 信息补偿剩余权重
        W[remaining] -= error * H_inv[remaining, group] / H_inv[group, group]

GGUF(GPT-Generated Unified Format)

GGUF 是 llama.cpp 项目定义的量化模型格式。自包含(单文件含架构、分词器、量化参数),支持多种量化方案(Q4_0, Q5_K_M, Q8_0 等),K-quants 使用混合精度(重要层更高精度)。GGUF 对 CPU 友好(利用 AVX/NEON 等 SIMD 指令),但 GPU 上的量化精度通常不如 AWQ/GPTQ。

KV Cache 量化

长上下文下 KV Cache 内存占用成为瓶颈。vLLM 的 FlashAttention 后端支持 FP8 KV Cache(torch.float8_e4m3fn,需 FlashAttention 3):

KV Cache 精度Perplexity(LLaMA2-7B, WikiText-2)相对 FP16 变化
FP16 (baseline)12.35-
INT8 (per-token)12.38+0.03
INT4 (per-token)12.52+0.17
INT4 (group=128)12.41+0.06

INT8 KV Cache 量化几乎无损,INT4 需要 group-wise scaling 才能保持精度。

各量化方法对比

方法位宽量化对象压缩比(vs FP16)精度损失特殊要求
FP8 (E4M3)8权重/激活/KV50%极小H100+ Tensor Core
INT88权重/激活50%小(需 SmoothQuant)INT8 Tensor Core
AWQ (INT4)4权重75%小-中特殊 kernel
GPTQ (INT4)4权重75%小-中广泛支持 (Marlin)
GGUF Q4_K_M4.5权重72%中等CPU 友好
FP8 KV Cache8KV Cache50%极小FA3 支持
INT8 KV Cache8KV Cache50%极小per-token

应用场景

  • FP8:生产环境中精度-效率最佳平衡点,H100 部署的标准选择
  • AWQ/GPTQ INT4:将 70B 模型从约 140GB 压缩到约 35GB,可在 2-4 张 GPU 上运行
  • GGUF:CPU 推理、边缘设备、本地隐私推理(llama.cpp 生态)
  • KV Cache 量化:长上下文服务(32K+),将 KV Cache 内存减半或更多,可显著提升支持的并发请求数

与其他概念的关系

量化直接降低模型参数和 KV Cache 的内存占用,从而减少推理所需的 GPU 数量和并行度(TP 可以更小)。量化后的模型与 Attention 后端紧密相关——FP8 KV Cache 需要 FlashAttention 3 支持,INT4 权重需要 Marlin 等特殊 kernel。AWQ/GPTQ 等量化方法也影响模型加载方式,vLLM 通过 quantization_config 区分不同格式。

4.4 Attention 优化后端

计算优化

Attention 优化后端是 LLM 推理中负责执行 Attention 计算的底层 kernel 实现。标准 Attention 的计算复杂度为 O(n2)(n = 序列长度),且内存访问模式差——需要多次读写 HBM(高带宽显存)。各种 Attention 后端通过 tiling、online softmax、算子融合等技术,在保持数学等价性的前提下大幅提升计算效率。

FlashAttention 1(2022)

核心创新是 Tiling + Online Softmax + Recomputation:

  • Tiling:将 Q/K/V 切分为小块(tile),在 SRAM 中完成局部计算,避免频繁读写 HBM。对于 Q tile Q_i(大小 B_r * d)和 K/V tiles K_j, V_j:
S_ij = Q_i @ K_j^T # 在 SRAM 中计算
m_ij = rowmax(S_ij)
P_ij = exp(S_ij - m_ij)
O_ij = P_ij @ V_j
  • Online Softmax:遍历 tiles 时增量更新全局统计量:
m_new = max(m_old, m_ij)
l_new = l_old * exp(m_old - m_new) + l_ij * exp(m_ij - m_new)
O_new = O_old * exp(m_old - m_new) + O_ij * exp(m_ij - m_new)
  • Recomputation:反向传播时不保存 S 矩阵(大小 n*n),而是反向时重新计算,将内存从 O(n2) 降到 O(n)。

IO 复杂度从 O(n2) 降低到 O(n2 / M)(M = SRAM 大小),实际获得 2-4 倍加速。

FlashAttention 2(2023)

主要改进:减少非矩阵乘法操作(online softmax 缩放与 GEMM 融合)、更好的 Warp 级并行(序列长度维度分配到不同 warps)、改进的 tile 划分策略。Forward 比 FA1 快约 2 倍,backward 快约 2-3 倍。

FlashAttention 3(2024,Hopper 专用)

利用 Hopper 架构硬件特性:

  1. TMA(Tensor Memory Accelerator):使用 cp.async.bulk 指令异步加载 tiles 到 shared memory
  2. Warp Group Cluster:将 4 个 warps(128 threads)组成 cluster 协作处理更大的 tile
  3. FP8 Tensor Core:原生支持 FP8 精度计算
  4. GEMM 和 Softmax 重叠:利用 Hopper 独立执行单元,当前 tile 计算与下个 tile 的 softmax 准备重叠

FA3 相比标准 attention 在 H100 上可达 4-6 倍加速(FP16)或 6-8 倍加速(FP8)。

FlashInfer

FlashInfer 是专门为 LLM 推理服务设计的 attention 引擎,vLLM V1 的默认 Attention 后端。核心优势:

  • Batch Decode Kernel:针对 decode 阶段(query_len=1)高度优化
  • Cascade Attention:对共享前缀的 batch 进行合并计算
  • Page Table 管理:原生支持非连续的 block table(PagedAttention)
  • 支持 FP8 KV Cache 和 MLA(Multi-head Latent Attention)

XFormers

XFormers 是 Facebook Research 开发的通用 Transformer 优化库,提供 memory-efficient attention。支持训练和推理,但 Paged KV 支持有限,Decode 阶段优化不如 FlashInfer,不支持 FP8 KV Cache。

各后端对比

特性FlashAttentionFlashInferXFormers
主要场景训练 + 推理推理(分页 KV cache)训练 + 推理
Paged KV 支持支持(v2+)原生支持有限支持
CUDA Graph支持支持支持
Decode 优化一般极强(Cascade/Append)一般
MLA 支持部分支持无
FP8 KV cacheFA3 支持支持不支持

vLLM V1 Attention Backend 架构

vLLM V1 对 attention backend 做了彻底重构,核心文件:

vllm/v1/attention/backend.py          # 抽象基类
vllm/v1/attention/backends/flash_attn.py   # FlashAttention 后端
vllm/v1/attention/backends/flashinfer.py   # FlashInfer 后端
vllm/v1/attention/backends/triton_attn.py  # Triton 后端
vllm/v1/attention/backends/mla/          # MLA 后端

AttentionBackend 定义抽象接口,AttentionMetadataBuilder 将 scheduler 输出的通用元数据(CommonAttentionMetadata)转换为后端特定格式(如 FlashAttentionMetadata)。Page size(block size)是关键超参数——小(如 16)减少内存碎片但 kernel 效率降低,大(如 128)计算效率高但内存浪费增加。vLLM 默认 block size = 16。

应用场景

  • FlashAttention:训练场景和不需要专门 decode 优化的推理场景
  • FlashInfer:vLLM V1 默认后端,适用于各种推理负载,尤其 decode-heavy 场景
  • XFormers:需要 memory-efficient attention 训练的通用场景,FlashAttention 不可用时的后备

与其他概念的关系

Attention 后端直接实现 PagedAttention 所需的非连续 KV Cache 访问(通过 block table 和 slot mapping)。FP8 KV Cache 量化依赖 FA3 或 FlashInfer 的 FP8 支持。MLA(Multi-head Latent Attention,DeepSeek-V2/V3 使用)需要专门的 MLA Attention 后端。不同的 Attention 后端影响 KV Cache 的物理布局(NHD vs HND)和 block size 限制。

4.5 采样策略(Sampling Strategies)

输出控制

采样策略决定了 LLM 在每次生成时如何从 logits 概率分布中选择下一个 token。不同的采样策略在输出确定性、多样性、创造性和可控性之间做不同的权衡。vLLM 通过 SamplingParams 类统一管理所有采样参数,在 vllm/v1/sampler/ 中实现采样逻辑。

Greedy Decoding(贪心解码)

每一步选择概率最高的 token:

next_token = argmax(logits)

这是确定性策略,适合代码生成、数学推导等需要精确输出的任务。vLLM 中当 temperature < 1e-5 时自动切换到 greedy。输出的多样性和创造力最差。

Temperature Sampling(温度采样)

通过对 logits 除以温度系数 T 来控制分布的"尖锐程度":

P(x_i) = exp(logit_i / T) / Σ_j exp(logit_j / T)
  • T -> 0:分布趋于尖锐,退化为 greedy
  • T = 1:保持原始分布
  • T > 1:分布趋于平缓,低概率 token 有更多机会被选中

vLLM 将 0 < temperature < 0.01 的值钳位到 0.01,避免数值溢出。

Top-p (Nucleus) Sampling

按累积概率截断候选集合:

V^(p) = {v_1, ..., v_k} 其中 Σ_{i=1}^{k-1} P(v_i) < p <= Σ_{i=1}^k P(v_i)

按概率从高到低排序 token,选择累积概率 >= p 的最小集合,在集合内重新归一化采样。Top-p 的优点是动态调整候选集大小——概率分布尖锐时候选集小,平坦时候选集大。vLLM 约束:0.0 < top_p <= 1.0。

Top-k Sampling

只保留概率最高的 k 个 token,重新归一化后采样。vLLM 中 top_k = 0 或 -1 表示禁用(考虑所有 tokens)。常与 Top-p 组合使用:先 Top-k 截断,再 Top-p 截断。

Beam Search(束搜索)

维护 beam_width 个候选序列,每步扩展所有候选并保留得分最高的 beam_width 个:

class BeamSearchParams(msgspec.Struct):
    beam_width: int
    max_tokens: int
    ignore_eos: bool = False
    temperature: float = 0.0
    length_penalty: float = 1.0      # > 1 偏好短序列, < 1 偏好长序列

Beam Search 适合翻译、摘要等需要全局最优的任务,但计算开销随 beam_width 线性增长,且容易产生重复。

Repetition Penalty(重复惩罚)

三种惩罚机制解决 LLM 的重复生成问题:

  • Repetition Penalty:对已出现 token 的 logits 直接缩放:
if token in generated_so_far:
logits[token] /= repetition_penalty # > 1 抑制重复
  • Frequency Penalty(频率惩罚):按出现次数线性惩罚:
logits[token] -= frequency_penalty * count[token]
  • Presence Penalty(存在惩罚):只要出现过就固定惩罚(二元):
if token in generated_so_far:
logits[token] -= presence_penalty

两者区别:Frequency Penalty 随出现次数线性增长(出现越多惩罚越大),Presence Penalty 只要出现过一次就恒定制裁。vLLM 约束范围为 [-2.0, 2.0]。

vLLM 还新增了 N-gram 重复检测机制:当检测到某 N-gram 模式重复 min_count 次时,提前终止生成。

各策略适用场景对比

策略确定性多样性可控性计算开销适用场景
Greedy最高最低最高最低代码生成、数学推导
Temperature中高中低创意写作、对话
Top-p中高(自适应)中低通用(最常用)
Top-k中中低低需控制候选数
Top-k + Top-p中高高低推荐组合
Beam Search高低高高翻译、摘要
Repetition Penalty--辅助极低与任何策略组合

应用场景

  • Greedy:准确性优先的生产环境(代码补全、SQL 生成),如 GitHub Copilot 的某些场景
  • Temperature + Top-p:创意写作、对话系统、故事生成,是最常用的组合(典型 T=0.7, top_p=0.9)
  • Beam Search:机器翻译、文本摘要、语音识别(需要全局最优序列)
  • Repetition Penalty:与任何采样策略搭配,解决长文本生成中的重复问题

与其他概念的关系

采样策略是 LLM 推理的最终输出环节,与 Attention 计算通过 logits 张量连接。Speculative Decoding 需要特殊的 modified rejection sampling 以保证采样一致性(与直接采样大模型分布一致),当前 vLLM 的 speculative decoding 不支持 min_p 和 logit_bias。采样参数通过 SamplingParams 类传递,与 Chunked Prefill、Continuous Batching 等调度机制协同工作。

4.6 推理引擎对比

系统集成

LLM 推理引擎是将模型加载、内存管理、计算调度、采样输出等环节集成在一起的生产级服务系统。不同引擎在核心创新、优化方向、硬件支持和生态集成方面存在显著差异。当前主流引擎包括 vLLM、TGI(Text Generation Inference)、TensorRT-LLM、SGLang 和 llama.cpp。

vLLM

vLLM 的核心创新是 PagedAttention,借鉴操作系统虚拟内存的分页思想解决 KV Cache 内存管理问题。支持 Continuous Batching、Chunked Prefill、Prefix Caching、Speculative Decoding、多种量化格式(FP8/AWQ/GPTQ/GGUF)、Tensor/Pipeline/Data/Expert 并行、Disaggregated Serving(Mooncake/NIXL/LMCache)。vLLM V1 架构重构了 Attention Backend,默认使用 FlashInfer。支持 NVIDIA/AMD/Intel/XPU 多平台。

TGI(Text Generation Inference)

HuggingFace 开发的 LLM 推理服务器,强调与 HuggingFace 生态的紧密集成。核心特性:Safetensors 格式加载(更快更安全)、内置 FlashAttention、Continuous Batching、Tensor Parallelism、量化支持(GPTQ/AWQ/BitsAndBytes)、原生 SSE 流式输出。TGI 的易用性最高(与 HuggingFace Hub 无缝集成),但在高吞吐场景下性能通常低于 vLLM(缺少 PagedAttention 的内存管理优势)。

TensorRT-LLM

NVIDIA 推出的 LLM 推理优化框架,基于 TensorRT 深度学习编译器,专注于在 NVIDIA GPU 上榨取最大性能。核心优化技术:

  • Kernel Fusion:将多个小算子合成为单个 CUDA kernel,减少 launch 开销
  • Plugin 系统:预优化 custom kernel(FMHA, GptAttentionPlugin)
  • Inflight Batching:NVIDIA 版本的 continuous batching
  • 量化:FP8/INT8/INT4, SmoothQuant, FP8 Transformer Engine

优势是极致性能(通常最高吞吐量),但平台锁定(仅 NVIDIA GPU)、编译时间长(数分钟到数小时)、灵活性低(支持新模型需写 plugin)。

SGLang

由伯克利大学(与 vLLM 同一团队)开发的推理框架,核心创新:

  • RadixAttention:使用 Radix Tree(基数树)管理 KV Cache,自动检测和复用共享前缀,比 vLLM 的块级哈希更灵活
  • Structured Generation:使用正则表达式或 CFG 约束模型生成(JSON/SQL 等)
  • 提供领域特定语言(DSL)用于结构化控制生成过程

SGLang 在多轮对话、结构化输出场景有独特优势,前缀复用场景下 TTFT 比 vLLM 快 2-6 倍。SGLang 部署规模已达 400,000+ GPU。

llama.cpp

完全使用 C/C++ 编写,不依赖 PyTorch 或 CUDA,目标是让 LLM 推理在消费级硬件上运行。核心特点:

  • GGUF 格式:自包含模型文件,支持多种量化(Q4_0/Q5_K_M/Q8_0 等)
  • CPU 优化:AVX/AVX-512/NEON SIMD 指令加速,高效多线程
  • 混合精度:CPU 上 INT8/INT4 量化推理
  • 多后端:除 CPU 外支持 Apple Silicon GPU(Metal)、Vulkan 兼容 GPU

性能在 GPU 上远低于前四个引擎,但在 CPU 和边缘设备上是唯一可行选择。

综合对比

引擎最佳场景吞吐量延迟易用性硬件支持
vLLM高吞吐生产服务、多租户极高低中NVIDIA/AMD/Intel/XPU
TGIHuggingFace 生态集成、快速部署高低高NVIDIA/Intel
TensorRT-LLMNVIDIA GPU 极致性能、企业级最高最低低NVIDIA only
SGLang多轮对话、结构化生成、Agent高低中NVIDIA/AMD
llama.cpp本地/边缘推理、CPU 部署、隐私低高高CPU/GPU/Metal

性能数据参考(LLaMA-2 70B, 8xA100):

引擎吞吐量 (tokens/s)TTFT批处理能力
vLLM2000-4000~100ms优秀
TensorRT-LLM3000-5000~80ms优秀
TGI1500-3000~120ms良好
SGLang2000-3500~100ms良好
llama.cpp (Q4)50-100 (CPU)~数秒有限

架构差异总结

  • 内存管理:vLLM 的 PagedAttention 通过分页消除碎片(<5% 浪费),TGI 使用传统连续分配(60-80% 浪费),SGLang 的 RadixAttention 通过树结构实现更灵活的前缀共享
  • 并行策略:vLLM 支持最全面的并行组合(TP+PP+DP+EP+DCP+PCP),TensorRT-LLM 聚焦 TP 和 PP,TGI 主要支持 TP
  • 量化生态:TensorRT-LLM 对 NVIDIA 量化格式支持最深(FP8、INT4 权重、SmoothQuant),vLLM 覆盖最广(FP8/AWQ/GPTQ/GGUF),llama.cpp 以 GGUF K-quants 著称
  • 部署运维:TGI 最易部署(一行命令),TensorRT-LLM 需编译+Triton Server,vLLM 和 SGLang 作为 Python 库灵活但需自行编排

应用场景

  • 生产高吞吐:vLLM 或 TensorRT-LLM。vLLM 更灵活(多平台、多量化),TensorRT-LLM 在纯 NVIDIA 环境中延迟最优
  • 快速原型/HF 生态:TGI,一行命令启动推理
  • 多轮对话/Agent 系统:SGLang,RadixAttention 和 Structured Outputs 原生优势
  • 本地隐私推理:llama.cpp,数据不出机器,支持 CPU 运行
  • 边缘/移动:llama.cpp(Metal/NEON 加速)

与其他概念的关系

推理引擎是 vLLM 概念体系的上层集成者——它将 PagedAttention、Continuous Batching、Chunked Prefill、Prefix Caching、模型并行、量化、Attention 后端等所有概念整合为统一服务。引擎对比揭示了不同设计取舍:vLLM 以内存管理创新驱动通用高性能,TensorRT-LLM 以编译优化驱动极限性能,SGLang 以编程范式创新驱动特殊场景优化。

模块四概念依赖关系总结

体系
  • 模型并行策略(4.1) 是分布式推理的基础架构层,决定了 GPU 资源的组织方式
  • Disaggregated Serving(4.2) 在并行策略之上按计算阶段分离资源,需要 KV Cache 跨节点传输
  • 量化(4.3) 是内存压缩技术,降低对并行度(TP size)的要求
  • Attention 后端(4.4) 是计算优化层,直接实现 PagedAttention 的底层 kernel
  • 采样策略(4.5) 是输出控制层,位于推理流水线的末梢
  • 推理引擎对比(4.6) 是系统集成层,展示各组件如何在不同引擎中以不同方式组合
← 上一模块
vLLM API 模型类型
下一模块 →
生态项目