作者:初七123
链接:https://www.jianshu.com/p/8c0e7edbefb9
来源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

------------------------------------------------------------------------------------

(深度神经网络的分布式计算范式 --------------   环形全局规约)   (副标题    自起)

------------------------------------------------------------------------------------

The Communication Problem

当将神经网络的训练并行化到许多GPU上时,你必须选择如何将不同的操作分配到你可用的不同GPU上。在这里,我们关注一种称为数据并行随机梯度下降( SGD )的技术。与标准SGD一样,梯度下降是通过数据子集(小批次)完成的,需要多次迭代才能在整个数据集上进行。然而,在数据并行训练中,每个GPU都有整个神经网络模型的完整副本,对于每次迭代,只分配了小批次中样本的子集。对于每次迭代,每个GPU在其数据上运行网络的前向传播,随后进行误差反向传播,以计算损耗相对于网络参数的梯度。最后,GPU相互通信以平均由不同GPU计算的梯度,将平均梯度应用于权重以获得新权重。GPU都在锁定步骤的迭代中前进,一旦GPU完成了迭代,它必须等待所有其他GPU完成它们的迭代,这样权重才能被正确更新。这相当于在单个GPU上执行SGD,但是我们通过在多个GPU之间分发数据并行执行计算来获得加速。

 
当你只有两个GPU和以兆字节数据衡量的参数时,这些GPU的通信方式可能并不重要。然而,当你的模型有数十亿个参数时,梯度可能需要几十亿字节的空间(因为每个参数都有一个梯度值),并且你正在协调几十个GPU,通信机制变得至关重要。
 
例如,考虑最直接的通信机制。每一个GPU都计算其子集的小批次上的梯度。然后,每个GPU将其梯度发送到单个GPU,该GPU取所有梯度的平均值,并将平均值发送回所有其他GPU。
 
在直接从单个GPU发送和接收数据的机制中,单个GPU必须从所有GPU接收所有参数,并将所有参数发送到所有GPU。系统中的gpu越多,通信成本就越大。
 
 
 
 
让我们评估一下这种通信策略如何在真实模型上运行,例如以百度深度语音2 为模型的语音识别网络,具有三亿个可训练参数。 每个参数四个字节的三亿个参数大约是1.2千兆字节的数据。 假设您系统上的网络硬件可以支持每秒1千兆字节的带宽; 在这种情况下,如上所述将系统并行化到两个GPU上将使每次迭代减慢1.2秒。 将您的训练并行化到10个GPU将使每次迭代减慢10.8秒; 随着GPU数量的增长,每次迭代所需的时间呈线性增长。 即使每次迭代花费几秒钟,通信成本的这种线性增长也会使得进一步的并行化变得不切实际并且会降低训练效率。
 
 

需要发送的数据越多,发送时间就越长;每个通信通道都有一个最大的吞吐量(带宽)。例如,一个好的internet连接可以提供每秒15兆字节的带宽,而千兆以太网连接可以提供每秒125兆字节的带宽。HPC集群上的专用网络硬件(如Infiniband)可以在节点之间提供每秒数gb的带宽

 
 
另一种选择是放弃训练算法的同步性,并通过梯度下降的迭代消除所有GPU在锁定步骤中前进的限制。然而,虽然这可以使模型更容易并行化,但是消除这种约束的算法(异步SGD的变体)可能很难调试,对于某些模型来说,可能会收敛到子结果,所以我们不考虑这些问题。

 

相反,我们可以通过使用高性能计算领域分布式缩减算法并利用带宽优化环来解决通信问题。

 
 
 
 
 
 
 
 
 
 

The Ring Allreduce

上述  简单  通信策略  的主要问题是,通信成本随系统中gpu的数量线性增长。相比之下,环allreduce算法的通信成本是恒定的,与系统中gpu的数量无关,完全由系统中gpu之间最慢的连接决定;事实上,如果您只考虑带宽作为通信成本的一个因素(并忽略延迟),那么环allreduce是一种最优通信算法(当您的模型很大,并且您需要发送大量数据的次数很少时,这是一个很好的通信成本估算。)。

环中的gpu都被安排在一个逻辑环中。每个GPU应该有一个左邻和一个右邻;它只会向它的右邻居发送数据,并从它的左邻居接收数据。

 
该算法分两个步骤进行:首先是scatter-reduce,然后是all-gather。在scatter-reduce步骤中,GPU将交换数据,使每个GPU可得到最终结果的一个块。在all-gather步骤中,gpu将交换这些块,以便所有gpu得到完整的最终结果。

 
 
 
 
 
 
 
 

The Scatter-Reduce

为简单起见,让我们假设目标是对一个浮点数的大数组求和; 系统中有N个GPU,每个GPU都有一个相同大小的数组,并且在all-reduce阶段的最后,每个GPU都应该有一个相同大小的数组,其中包含原始数组中数字的总和。
 

首先,gpu将数组划分为N个更小的块(其中N是环中的gpu数)。

 
 

接下来,GPU将进行N-1Scatter-Reduce 迭代;在每次迭代中,GPU将向其右邻居发送一个块,并从其左邻居接收一个块并累积到该块中。每个GPU发送和接收的块在每次迭代中都是不同的;第n个GPU从发送块N和接收块N - 1开始,然后从那里向后进行,每次迭代都发送它在前一次迭代中接收到的块。
 
 
 

例如,在第一次迭代中,上图中的五个GPU将发送和接收以下区块:



Data transfers in the first iteration of scatter-reduce
 
 
 

在第一次发送和接收完成之后,每个GPU将拥有一个块,该块由两个不同GPU上相同块的和组成。例如,第二个GPU上的第一个块将是该块中来自第二个GPU和第一个GPU的值的和。

 
 
 
 

Itermediate sums after the first iteration of scatter-reduce is complete
 
 
 
 
 
 
 
 
 
在下一次迭代中,该过程继续进行,到最后,每个GPU将有一个块,该块包含所有GPU中该块中所有值的总和。下图展示了所有数据传输和中间结果,从第一次迭代开始,一直持续到Scatter-Reduce完成。
 

 

 
 
 
 
 
 
 

The Allgather

scatter-reduce步骤完成之后,每个GPU都有一个值数组,其中一些值(每个GPU一个块)是最终的值,其中包括来自所有GPU的贡献。为了完成all-reduce, gpu必须交换这些块,以便所有gpu都具有所有必需的值。
环的收集过程与scatter-reduce是相同的(发送和接收的N-1次迭代),只是gpu接收的值没有累加,而是简单地覆盖块。第n个GPU首先发送第n+1个块并接收第n个块,然后在以后的迭代中总是发送它刚刚接收到的块。

 
 
 

例如,在我们的5 - gpu设置的第一次迭代中,gpu将发送和接收以下块

第一次迭代完成后,每个GPU将拥有最终数组的两个块。

 
 
 
 
 
 
 
在下一个迭代中,该过程将继续,到最后,每个GPU将拥有整个数组的完整累积值。下面的图像演示了所有数据传输和中间结果,从第一次迭代开始,一直到all-gather完成。
 

 

 
 
 
 
 
 
 
 
 
 

All-reduce Communication Cost

回想一下,对于介绍中描述的简单通信算法,通信成本随着GPU的数量线性增长。 all-reduce运行良好的主要原因是不再是这种情况。
 
 
 
在我们描述的系统中,N个GPU中的每一个都将发送和接收N-1scatter-reduceN-1all-gather。每次,GPU都会发送K / N值,其中K是数组中不同GPU上相加的值总数(K为每个GPU上所需存储数组的总大小)。因此,传输到每个GPU和从每个GPU传输的数据总量为

重要的是,这与GPU的数量无关。

 
 
 
 
由于所有传输都是在离散迭代中同步进行的,因此所有传输的速度受到环中相邻GPU之间最慢(最低带宽)连接的限制。给定每个GPU的邻居的正确选择,该算法是带宽最优的,并且是执行全面操作的最快算法(假设延迟成本与带宽相比可以忽略不计)。一般来说,如果一个节点上的所有GPU在环中彼此相邻,则该算法的功能最佳;这最小化了网络争用的量,否则这可能会显著降低GPU-GPU连接的有效带宽。

 
 
 
 
 
 
 
 

Applying the Allreduce to Deep Learning

Ring all-reduce 是高性能计算领域中著名的算法,但在深度学习中很少使用。在我们的实验室中,我们已经成功地将这个工具作为所有数据并行训练的基础,使我们能够有效地将训练扩展到几十个gpu。
 
 
 
为了最小化通信开销,我们可以利用神经网络的结构。在每次迭代中,每个GPU运行正向传播来计算误差,然后运行反向传播来计算神经网络的每个参数的梯度。反向传播计算梯度,从输出层开始,向输入层移动,这意味着输出层参数的梯度在早期层的梯度计算出之前很明显是可用的。因为全部运算可以一次对网络的一部分参数进行运算,所以我们可以在其他梯度仍在计算的时候开始对输出层参数进行全部运算。这样做将通信与反向传播步骤中的其余计算重叠,从而减少了每个GPU等待通信完成的总时间。
 
 
例如,考虑一个类似于2的语言模型,但有大约3亿个可学习的参数(因此总梯度大小为1.2千兆字节)。 使用all-reduce,每个GPU必须发送和接收大约2.4千兆字节的数据。 使用支持CUDA的MPI实现(例如OpenMPI),我们可以使用GPUDirect RDMA在GPU之间传输数据,带宽大约为每秒10千兆字节; 但是,我们集群中节点之间的连接速度较慢,Infiniband提供的带宽大约为每秒6千兆字节。 由于限制因素是Infiniband连接,因此单次迭代需要大约

由于更深层次的网络首先有可用的梯度,我们可以在完成整个反向传播传递之前开始进行数据传输,因此真正的开销可能小于400毫秒;根据所优化的神经网络的性质,通信和计算之间的重叠可能有所不同。
 
 
 
 
 
 
 
 
 
我们实现了上述语言模型,并测试了每次迭代所花费的时间,因为我们从单个GPU(没有通信开销)扩展到40个GPU。 这40个GPU排列成5个节点每个节点有8个GPU,由Infiniband连接。 我们运行语言模型300次迭代,批量大小为32,并计算每秒处理的样本数。

 
 
 
 
正如您所看到的,整个系统的吞吐量随着GPU的数量线性扩展;超过一定的节点后,添加更多的GPU不会导致每次迭代的显著减速。在40个GPU上运行模型每次迭代大约需要650 - 700毫秒,而在单个GPU上大约需要370毫秒。根据我们的估计,通信将花费400毫秒,通过将反向传播与数据传输重叠,我们在每次迭代中节省了额外的70 - 120毫秒。

 
 
 
 
 
 -----------------------------------------------------------
 
 
 转者注:
实现本文深度神经网络的ring all-reuce模式多数成型框架一般需采用NVIDIA公司的nccl框架。
 
 
 
 
 

【转载】 Ring Allreduce (深度神经网络的分布式计算范式 -------------- 环形全局规约)的更多相关文章

  1. TensorFlow 深度学习笔记 TensorFlow实现与优化深度神经网络

    转载请注明作者:梦里风林 Github工程地址:https://github.com/ahangchen/GDLnotes 欢迎star,有问题可以到Issue区讨论 官方教程地址 视频/字幕下载 全 ...

  2. TensorFlow实现与优化深度神经网络

    TensorFlow实现与优化深度神经网络 转载请注明作者:梦里风林Github工程地址:https://github.com/ahangchen/GDLnotes欢迎star,有问题可以到Issue ...

  3. 如何用70行Java代码实现深度神经网络算法

    http://www.tuicool.com/articles/MfYjQfV 如何用70行Java代码实现深度神经网络算法 时间 2016-02-18 10:46:17  ITeye 原文  htt ...

  4. 深度神经网络(DNN)模型与前向传播算法

    深度神经网络(Deep Neural Networks, 以下简称DNN)是深度学习的基础,而要理解DNN,首先我们要理解DNN模型,下面我们就对DNN的模型与前向传播算法做一个总结. 1. 从感知机 ...

  5. 深度神经网络(DNN)反向传播算法(BP)

    在深度神经网络(DNN)模型与前向传播算法中,我们对DNN的模型和前向传播算法做了总结,这里我们更进一步,对DNN的反向传播算法(Back Propagation,BP)做一个总结. 1. DNN反向 ...

  6. 深度神经网络(DNN)损失函数和激活函数的选择

    在深度神经网络(DNN)反向传播算法(BP)中,我们对DNN的前向反向传播算法的使用做了总结.里面使用的损失函数是均方差,而激活函数是Sigmoid.实际上DNN可以使用的损失函数和激活函数不少.这些 ...

  7. 深度神经网络(DNN)的正则化

    和普通的机器学习算法一样,DNN也会遇到过拟合的问题,需要考虑泛化,这里我们就对DNN的正则化方法做一个总结. 1. DNN的L1&L2正则化 想到正则化,我们首先想到的就是L1正则化和L2正 ...

  8. 最大似然估计 (Maximum Likelihood Estimation), 交叉熵 (Cross Entropy) 与深度神经网络

    最近在看深度学习的"花书" (也就是Ian Goodfellow那本了),第五章机器学习基础部分的解释很精华,对比PRML少了很多复杂的推理,比较适合闲暇的时候翻开看看.今天准备写 ...

  9. 神经网络 之 DNN(深度神经网络) 介绍

    CNN(卷积神经网络).RNN(循环神经网络).DNN(深度神经网络) CNN 专门解决图像问题的,可用把它看作特征提取层,放在输入层上,最后用MLP 做分类. RNN 专门解决时间序列问题的,用来提 ...

  10. AlphaGo论文的译文,用深度神经网络和树搜索征服围棋:Mastering the game of Go with deep neural networks and tree search

    转载请声明 http://blog.csdn.net/u013390476/article/details/50925347 前言: 围棋的英文是 the game of Go,标题翻译为:<用 ...

随机推荐

  1. 夜莺监控 v7.beta4 发版,仪表盘变量和业务组下的机器联动

    这个版本最大的改动,就是仪表盘变量和业务组下的机器联动.大家可以导入这个大盘做测试: https://github.com/ccfos/nightingale/blob/main/integratio ...

  2. json字符串忽略null,忽略字段,首字母大写等gson,jackson,fastJson实现demo,T data JSON.parseObject json转换

    json字符串忽略null,忽略字段,首字母大写等gson,jackson,fastJson实现demo package com.example.core.mydemo.json.vo; import ...

  3. 解决NodeJS Downloading node-sass 卡死慢安装失败的问题

    之前写过一篇从0开始的NodeJS安装配置教程,在那篇文章结尾提到使用过程中还有一个坑,只是没有遇到就没写,时隔多日在我使用某开源项目的时候又遇到了这个问题 下载依赖时一直卡在 Downloading ...

  4. 有点儿神奇,原来vue3的setup语法糖中组件无需注册因为这个

    前言 众所周知,在vue2的时候使用一个vue组件要么全局注册,要么局部注册.但是在setup语法糖中直接将组件import导入无需注册就可以使用,你知道这是为什么呢?注:本文中使用的vue版本为3. ...

  5. 3562-Linux系统使用手册

  6. vulnhub - NYX: 1

    vulnhub - NYX: 1 描述 这是一个简单的盒子,非常基本的东西. 它是基于vmware的,我不知道它是否可以在VB上运行,如果你愿意的话可以测试一下. /home/$user/user.t ...

  7. 【一天一点.NET小知识】运用向量Vector<T>加速求和计算

    随着 .NET 版本的演进,从 .NET Standard 2.0 版本开始,支持 Vector<T> 类型. Vector<T> 类型:表示指定数值类型(适用于并行算法的低级 ...

  8. C#使用SendMessage进行进程间通讯

    最近公司有个需求是,拖动文件到桌面图标上,自动打开文件.那么只需在OnStartup事件中通过StartupEventArgs获取文件名然后进行操作即可.操作之后发现当软件已经启动了(单例运行),那么 ...

  9. Solo 开发者周刊 (第4期):什么样的新科技,能提高生活效率?

    这里会整合 Solo 社区每周推广内容.产品模块或活动投稿,每周五发布.在这期周刊中,我们将深入探讨开源软件产品的开发旅程,分享来自一线独立开发者的经验和见解.本杂志开源,欢迎投稿. 好文推荐 AI生 ...

  10. [oeasy]python0119_语言的演化_拉丁字符_罗马帝国_罗马体

    罗马拉丁字符 回忆上次内容 起源于埃及的 圣书体 象形文字 在与 两河流域的 苏美尔楔形文字 结合后 经过 腓尼基人 的拼音化 和 广泛传播 终于来到了 希腊   ​   添加图片注释,不超过 140 ...