跳转到正文
宋柏成
返回

大模型并行的几种切法

八张卡,不等于八张卡同时算同一道题。有的配置让八张卡分别接八组请求,有的让八张卡合作算一条请求,还有的让模型在不同机器之间接力。

看见 DP=4、TP=2,先不要把数字当成性能倍数。它们描述的是分工方式,不是“速度翻几倍”。

先列出来

名称切什么想解决什么要付出的代价
DP:数据并行请求或训练 batch多份副本同时干活,提高吞吐重复存权重;训练还要同步梯度
TP:张量并行层内的权重矩阵和计算一份模型跨多卡,分摊显存和计算层内频繁通信
PP:流水线并行模型的层各卡保存不同层,让大模型放得下顺序依赖、流水线气泡、阶段不均衡
EP:专家并行MoE 的专家分摊专家权重和计算token 路由通信、专家负载不均衡
CP:上下文并行单个序列的位置处理很长的序列跨分片的注意力通信

这里先区分训练和推理。训练有反向传播、梯度和优化器状态;推理通常没有这些,但需要为请求保存 KV cache。名称相同,不代表两种场景的通信和显存开销相同。

DP:多开几家一样的店

在纯推理、模型能放进单卡的前提下,DP=8 可以是八份模型副本,每份接自己的请求。一个入口负责分发请求,八份副本分别工作。

GPU 0:完整模型 → 请求 A
GPU 1:完整模型 → 请求 B
……
GPU 7:完整模型 → 请求 H

服务启动时就有这些副本,不是每来一条请求重新复制一次模型。每份副本还能批量处理多个请求,DP 数字也不是最大并发人数。

DP 主要增加总吞吐,而不是让一个人的回答快八倍。纯 DP 的一条请求仍在一个副本里执行。模型本身单卡放不下,多复制七份并不能解决问题。

普通推理副本不必为了每一层计算互相同步。训练 DP 则不同:各副本吃不同的数据,计算梯度,然后同步或归约梯度,让模型参数继续保持一致。训练框架还可能用 ZeRO 或 FSDP 分片模型状态,因此“所有 DP 都在每张卡上保存全部训练状态”也不准确。

DP 还可以和 TP、PP 混用。此时一份 DP 副本本身可能横跨多张卡,而不是一份副本固定等于一张卡。

TP:同一道矩阵题,大家各算一部分

TP 切的是层内计算。以线性层 Y = X × A 为例,把权重 A 按列切成两块:

A = [A1 | A2]
GPU 0 算 Y1 = X × A1
GPU 1 算 Y2 = X × A2

两张卡各得到一半输出。逐元素的非线性函数可以在两张卡上分别做,不必先拼成完整输出。

下一层再把权重按行切,直接使用各卡已有的本地输出:

Z = Y1 × B1 + Y2 × B2

各卡先算部分和,再通过 all-reduce 等集合通信合成结果。all-reduce 可以理解为“把大家的部分结果归约,然后让参与者都得到结果”。

经典 Megatron 的前馈块可在输出处归约一次,注意力块还另有通信。因此不能说“整个 Transformer 层前向固定只有一次 all-reduce”,实际次数由模型和实现决定。

TP 能分摊权重,并让多卡参与同一条请求的计算。但计算中间要频繁交流,互联慢时,GPU 会花很多时间等结果。并行度过大还会把本地矩阵切得太小,计算内核利用率下降。

所以 TP 通常优先放在高速互联域内,例如有 NVLink/NVSwitch 的节点。跨机 TP 不是不能做,而是需要足够好的网络和实测结果。没有“TP=8 一定好、TP=16 一定差”的通用阈值。

PP:前面的算完,交给后面的

PP 按层分段。例如 80 层模型分成两段:

GPU 0:层 1~40 → GPU 1:层 41~80

第一张卡把中间激活传给第二张,第二张继续计算。一份模型因此能分摊到两张卡的显存中,但不是两张卡同时算同一层。

如果只有一份工作在流水线上,前一段计算时后一段等待,后一段计算时前一段可能等待。这个空闲叫流水线气泡。把批次切成多个 microbatch,让不同段同时处理不同 microbatch,可以摊薄气泡。

在各段耗时近似相等、忽略通信的简化训练模型中,气泡占比为:

(p - 1) / (m + p - 1)

p 是段数,m 是 microbatch 数。四段、八个 microbatch 时约 27%;四段、三十二个时约 8.6%。这是特定假设下的估计,不是线上推理 GPU 利用率的测量结果。

训练中的 GPipe 先做全部前向再做反向,需要保存较多激活。1F1B 在流水线填满后交替安排前向和反向,较早释放激活;它缓解内存压力,但不意味着可以无限加 microbatch。推理没有反向传播,调度和瓶颈要另看。

PP 的层内跨卡同步比 TP 少,因此常用于跨节点切层。但阶段不均衡、网络传递和单请求的顺序依赖仍会影响延迟。它能让模型放得下,不保证一条回答更快。

EP:把不同专家分给不同卡

MoE 模型的前馈部分包含多个专家,路由器为每个 token 选择少数专家。选择几个由模型决定,不固定是一两个。

EP 让不同卡持有不同专家。token 按路由结果送到专家所在卡,计算后再收回来。TP 则可把每个专家的矩阵都切开:这两种分法不同,但同样分片度下,EP 不一定天然比 TP 少存更多权重。

EP 的典型通信是 all-to-all:各卡相互分发和收回 token。它与 all-reduce 的模式不同,不能只按名字判断谁一定更重。token 数、专家选择、负载均衡和网络拓扑都影响成本。大规模 EP 可以跨节点,不只限于一台机器。

还要注意,专家层与注意力层未必采用同一种分法。例如 vLLM 支持数据并行注意力配专家并行。EP 组的规模和 TP、DP 的关系取决于框架,不能把 EP 无条件作为另一个独立乘数塞进总卡数公式。

CP:把一篇很长的内容分段处理

CP 切单个序列的位置,不是给不同卡分配互不相关的请求。

各卡处理自己的序列分片,但一个位置的注意力可能依赖其他分片。因此计算时要跨卡交换所需的 K/V 信息。ring attention 等实现可以分块传递、逐步累积,不要求每张卡始终保存完整序列的 K/V,也不固定为一次 all-to-all。

CP 常用于长序列训练,或框架支持的长上下文计算。推理里的 KV cache 分片还可能来自 TP 或其他机制,不能见到“长上下文”就断定用了 CP。

SP(序列并行)也容易混淆:Megatron 的 SP 常在 TP 组内对部分激活按序列维度分片,重点是减少激活占用;CP 则显式切分上下文并处理跨分片注意力。名字相近,配置语义不是一回事。

同样八张卡,DP=4、TP=2 到底怎么排

先约定没有 CP,未写出的并行度都是 1。对于普通、独立的 DP/TP/PP 分组:

总卡数 = DP × TP × PP

DP 是份数,TP 是每段内合作算矩阵的卡数,PP 是每份模型的流水线段数。

配置八卡分工主要方向
DP=8八份模型,每份一张卡单卡已放下,扩请求吞吐
TP=8一份模型,八张卡合作算层内矩阵分摊一份模型,评估通信与延迟
DP=4,TP=2四份模型,每份由两张卡做 TP分片和吞吐兼顾
DP=4,PP=2四份模型,每份两段,每段一张卡分层放下,再扩副本
DP=2,TP=2,PP=2两份模型,每份两段,每段两卡 TP三种分工组合

DP=4、PP=2 是四份副本,每份两张卡,没有 TP:

副本 A:GPU 0(前半层) → GPU 1(后半层)
副本 B:GPU 2(前半层) → GPU 3(后半层)
副本 C:GPU 4(前半层) → GPU 5(后半层)
副本 D:GPU 6(前半层) → GPU 7(后半层)

DP=4、TP=2 也是四份副本,但每份的两张卡在每一层合作,而不是前后接力:

副本 A:TP组(GPU 0、1)
副本 B:TP组(GPU 2、3)
副本 C:TP组(GPU 4、5)
副本 D:TP组(GPU 6、7)

DP=2、TP=2、PP=2 则是:

副本 A:TP组(0、1)第一段 → TP组(2、3)第二段
副本 B:TP组(4、5)第一段 → TP组(6、7)第二段

若是采用独立 CP 轴的典型 Megatron 训练配置,公式扩展为:

DP = world_size / (TP × PP × CP)

ZeRO Stage 2 中的“2”不是两张卡,也不是 DP=2。它指训练状态的分片阶段:Stage 1 分优化器状态,Stage 2 再分梯度,Stage 3 再分参数。DP=4 则是数据并行组大小。这两个数字不能直接相乘当作卡数。

一台八卡和两台四卡,有什么不同

同样八张卡、同样总显存,通信拓扑可能完全不同。

一台有 NVSwitch 的八卡服务器,所有卡之间可以有高速互联。两台四卡服务器,机内可能快,机外却由网卡带宽、延迟、RDMA 配置和交换机决定。消费级八卡主机也不等于 NVSwitch 八卡服务器,还要看 PCIe 插槽、P2P 和跨 CPU 拓扑。

如果模型需要四卡 TP 才能放下,两台四卡机器可以各跑一份 TP=4 副本,合起来 DP=2。请求分到其中一台,层内通信留在机内。

如果一份模型必须用八卡,两台四卡可以考虑 TP=4、PP=2:每台四卡做一个流水线段,段间跨机传激活。也可评估跨机 TP=8,但不能假设它与单机八卡性能相同。

vLLM 官方文档还给了两台八卡、共十六卡的例子:机内 TP=8,机器间 PP=2。它是一种利用拓扑的排法,不是所有模型必须照抄的配置。

最后按瓶颈选

TP 不保证 KV cache 能一直等比例减少。注意力头数、GQA/MQA 结构和实现都会影响分片,部分 KV 头可能被复制。DP 副本各保存自己请求的缓存,并不是每个副本都保存所有请求的缓存。

比较配置时,要同时看显存峰值、首 token 延迟、逐 token 延迟、总 tokens/s 和并发下的尾延迟。只测一个请求,就很难判断 DP 的吞吐价值;只看总吞吐,也看不见某个用户等了多久。

一句话:先问是放不下、单条太慢,还是请求太多,再问切哪一维。 八张卡只是资源数量,分工和互联才决定它们能干好什么。

官方资料与参考


分享这篇文章:

上一篇
本地模型该用哪套运行时
下一篇
RAG 与 LLM Wiki:两种 AI 知识库方式怎么选