🎀个人主页: https://zhangxiaoshu.blog.csdn.net
📢欢迎大家:关注🔍+点赞👍+评论📝+收藏⭐️,如有错误敬请指正!
💕未来很长,值得我们全力奔赴更美好的生活!
前言
对于深度学习模型的预训练阶段,海量的训练数据、超大规模的模型给深度学习带来了日益严峻的挑战,因此,经常需要使用多加速卡和多节点来并行化训练深度神经网络。目前,数据并行和模型并行作为两种在深度神经网络中常用的并行方式,分别针对不同的适用场景,有时也可将两种并行混合使用。本文对数据并行和模型并行两种在深度神经网络中常用的并行方式原理及其通信容量的计算方法进行介绍。
一、深度神经网络求解原理回顾
深度神经网络是通过模仿生物大脑的神经元结构而设计的一种多层互连结构.在其训练过程中,数据输入神经网络经过网络的前向传播过程得到一个输出,然后对输出得预测值和真实值求相对误差将其作为损失函数,接着,对网络进行反向传播求得损失对权重参数得梯度信息,最后,使用得到的梯度信息对权重参数做梯度下降使得损失函数越来越小,如此反复这个过程,使得神经网络的预测结果变得越来越准确。
假设训练数据集为
X
=
[
x
1
,
x
2
.
.
.
x
N
,
]
X=[x_1,x_2...x_N,]
X=[x1,x2...xN,],数据集经过前向传播后输出预测值
f
(
x
i
)
f(x_i)
f(xi),真实值为
y
i
y_i
yi,则损失函数可以表示为如下式所示。
R e m p ( f ) = 1 N ∑ i = 1 N L ( y i , f ( x i ) ) R_{emp}\left(f\right)=\frac{1}{N}\sum_{i=1}^{N}L\left(y_i,f\left(x_i\right)\right) Remp(f)=N1i=1∑NL(yi,f(xi))
其中, L ( ∙ ) L(\bullet) L(∙)为损失函数,它主要用于衡量预测值和真实值之间差异的大小,差异越小,说明模型的预测越准确。对于不同问题的求解,往往具有不同的形式。根据上式可以得到求解深度神经网络的最优化表达式如下式所示。
f ∗ = arg min f ∈ F R e m p ( f ) f^{*}=\underset{f \in \boldsymbol{F}}{\arg \min } R_{\mathrm{emp}}(f) f∗=f∈FargminRemp(f)
即在假设空间 F F F中找到一个最优的模型 f ∗ f^\ast f∗使得 R e m p ( f ) R_{emp}(f) Remp(f)最小。
基于梯度的优化算法是DL中解决上述优化问题应用最广泛的算法。由于二阶梯度下降法的计算复杂度较高,一阶梯度下降法,尤其是带有mini-batch及其变体的随机梯度下降法(SGD)在DL中被广泛使用。SGD的更新规则如下式所示。
G t ( x t ) = ∇ F t ( x t ; ξ t ) G_t\left(x_t\right)=\nabla F_t\left(x_t;\xi_t\right) Gt(xt)=∇Ft(xt;ξt)
x t + 1 = x t − γ G t ( x t ) x_{t+1}=x_t-\gamma G_t\left(x_t\right) xt+1=xt−γGt(xt)
这里的 x t ∈ R N x_t\in R^N xt∈RN是第 t t t次迭代时的N维模型参数, ξ t \xi_t ξt是随机抽样的小批量数据, γ \gamma γ是学习率(或步长)。SGD是一种迭代算法,迭代过程通常包含几个步骤:
- 它对一小批数据(即 ξ t \xi_t ξt)进行采样。
- 它执行前馈计算,以计算目标函数的损失值(即 F t ( x t ; ξ t ) F_t\left(x_t;\xi_t\right) Ft(xt;ξt))。
- 它执行反向传播以计算关于模型参数的梯度(即 ∇ F t ( x t ; ξ t ) ∇F_t\left(x_t;\xi_t\right) ∇Ft(xt;ξt))。
- 最后,通过公式 x t + 1 = x t − γ G t ( x t ) x_{t+1}=x_t-\gamma G_t\left(x_t\right) xt+1=xt−γGt(xt)更新模型参数。训练深层模型非常耗时,尤其是对于大型模型或数据集。使用分布式训练技术,利用多个处理器来加速训练过程变得很常见。
二、数据并行
数据并行是在不同设备上放置完整的模型,然后将数据划分在每个设备并行计算,如下图所示。
数据并行性是深度学习中普遍存在的一种技术,对每个输入批训练数据在所有设备之间分配,每个设备中存储着网络模型完整的权重。在更新模型权重之前,梯度在所有设备之间进行通信和聚合。数据并行性拥有计算效率高和易于实现等优点。然而,数据并行性依赖于数据并行工作块的数量来缩放批处理大小,并且不能在不影响模型质量的情况下任意增大。对于参数不能存储在单个设备的大型模型,数据并行性便不在适应。
在小型分布式规模下,数据并行可以具有非常不错的扩展性。然而,梯度聚合的通信成本随着深度学习模型大小的增大而增加,并极大的限制了大模型和较低通信带宽系统的训练效率。针对分布式深度学习的数据并行训练,其训练过程如下:
- 计算节点会从将硬盘或者网络中读出mini-batch大小的数据复制到内存中;
- 将数据从 CPU内存复制到 GPU内存;
- 加载GPU kernel并从前到后分层进行计算输入数据的预测值(正向传播);
- 计算预测值和真实值的损失函数(loss)并进行反向传播,逐层求出损失对权重参数的梯度值;
- 将各个结点的梯度值进行同步 (发送和接收梯度,即,梯度通信);
- 利用同步后的梯度值结合优化算法对神经网络的权重参数进行更新;
以上6步构成了一个神经网络的学习过程,也就是一个Itera。在实际训练中,为了实现对神经网络的参数进行训练,必须进行多次的训练。在以上的训练过程中,网络通信发生的环节为一、二、五步
。在第一步中,如果使用本机磁盘来提供资料,那么就不会有通信处理。第二步包括服务器之间的通信,这是用PCI-e把数据传送到 GPU。在第五步中,网络的参数量大小和规模主要由神经网络的参数和网络层的数目决定。在一般情况下,一个 Iter中的各个结点所需传送和接收的通信数据量均与神经网络的总参数值大小相等,而所需传送的数目则与神经网路的层数有关。所以,在每个层次上传送的通信数据量是不一样的,而频率区间也是由运算速度决定的。对于常见的CNN网络,其卷积层参数量要小于全连接层,所以在反向传输时,各个网络层的通信量会出现先大后小的不平衡问题。
因为数据并行需要每个设备将自己模型参数的梯度信息向其他设备传输。所以其通信容量往往与每一个批次的数据量多少无关,而与模型的大小和并行的设备数量有关。则对于深度神经网络的数据并行训练,其总的通信容量如下式所示。
V c o m m u n i c a t i o n = P a r × B y t e × N × ( N − 1 ) V_{communication}=Par×Byte×N×(N-1) Vcommunication=Par×Byte×N×(N−1)
其中 P a r Par Par表示模型的参数量, B y t e Byte Byte是参数的表示形式,单位为字节,深度神经网络训练时通常取4字节即32位来表示参数。 N N N为并行计算的设备数量。
三、模型并行
模型并行是将模型分割成不同的块放到不同的设备上,按照划分方式的不同主要有以下图所示两种形式。
在数据并行的情况下,整个模型都存储在内存中,不过有时会数据量很大。如果是一般的计算机,那么内存就会不够,面对这种情况,这个巨大的模型可以分解成不同的部分用不同的机器进行计算,从计算角度上讲,就是将张量分成几个部分,从模型上讲,就是将网络的结构分割开来。切分方法有两种,一种是垂直切分(左图),另一种是水平切分(右图)。
垂直切分时形成多个分区,相同的分区放在同一设备上,每一个分区在不同的设备上并行执行。在这种形式下,某一层某个神经元的输入只有此设备上来自上一层的特征,而位于其他设备上的输入却不能得到。因此,为了避免这种情况,需要在关键的一些层处进行设备之间的通信,以融合不同设备上的特征。对于第i层其总的通信容量如下式所示。
V i = o u t × B y t e × N × ( N − 1 ) V_i=out\times Byte\times N\times(N-1) Vi=out×Byte×N×(N−1)
其中 o u t out out表示每一个设备上输出的特征数量, B y t e Byte Byte是参数的表示形式,单位为字节, N N N为并行计算的设备数量。故,对于垂直切分时的模型并行来说其总的通信容量如下式所示。
V c o m m u n i c a t i o n = ∑ V i i ∈ ( 1 , 2... L ) V_{communication}=\sum V_i\ \ \ \ \ i\in(1,2...L) Vcommunication=∑Vi i∈(1,2...L)
其中 L L L表示模型总的层数,这里的 i i i根据具体情况选取 1 1 1到 L L L中的几个。
从以上两式中可以看到,对于垂直切分的模型并行来说,其通信容量主要受到输出特征值数量、选取的通信层数量、设备数量有关。
而对于水平切分,在这种模型并行形式下,可以将几个层划分给一个设备,不同设备划分得到的层不一致,因为在这种形式下后后面的层需要前面层的输出结果,每个设备要将自己计算的特征传输给下一层。所以前后阶段流水分批工作,然而,在这种情况下,第一个设备计算时,后面的设备都处于不工作状态,这很大程度上降低了并行性。 为了提高并行度,将每一个层再进行按区划分,第一个设备先执行第一个层的分区1,执行完之后开始执行分区2,这时设备2执行第二个层的分区1,如此反复计算传播以得到最终结果。对于水平切分时的模型并行来说其总的通信容量如下式所示。
V c o m m u n i c a t i o n = ∑ i = 1 N o u t i × B y t e V_{communication}=\sum_{i=1}^{N}{{out}_i\times B y t e} Vcommunication=i=1∑Nouti×Byte
其中 o u t i {out}_i outi表示第 i i i个设备的输出特征量, B y t e Byte Byte是参数的表示形式,单位为字节, N N N为并行计算的设备数量。
从上式中可以看到,对于水平切分的模型并行来说,其通信容量主要受输出特征值数量、设备数量等影响。
总结
数据并行和模型并行是在分布式计算中常用的两种并行计算策略,用于加速机器学习模型的训练过程。以下是它们的主要特点和区别总结:
数据并行(Data Parallelism):
- 特点: 在数据并行中,不同的处理单元(通常是不同的计算节点或设备)负责处理不同的数据子集。每个处理单元独立地计算模型的梯度,并在一定周期后进行参数更新。
- 优点: 数据并行易于实现,尤其是在拥有大量相似数据的情况下。它能够有效地利用大规模并行计算资源。
- 缺点: 数据传输和同步操作可能成为性能瓶颈,尤其是当模型参数量较大时。此外,对于某些较大的模型结构,数据并行可能会受到单卡GPU显存的限制。
模型并行(Model Parallelism):
- 特点: 在模型并行中,模型被划分成多个部分,不同的处理单元负责计算不同部分的输出。这通常用于处理较大且无法完全放入内存的模型。
- 优点: 模型并行可以处理超大规模的模型,因为不需要一次性加载整个模型。这对于深度、复杂的模型是一个重要的优势。
- 缺点: 实现模型并行通常较为复杂,因为需要确保各个部分的输出正确传递并在联合训练中协同工作。此外,同步问题也可能影响性能。
总体而言,数据并行和模型并行通常可以结合使用,以充分发挥分布式计算资源的优势。同时,具体选择使用哪种并行策略取决于问题的性质、模型的结构以及可用的硬件资源。
另外,在部分其他文献或是介绍中,模型并行的垂直切分往往被称之为Tensor并行
,而模型并行的水平切分往往被称之为流水并行
,
文中有不对的地方欢迎指正。