分佈式深度學習:神經網絡的分佈式訓練

分佈式深度學習:神經網絡的分佈式訓練

2016-10-09 14:05:04         http://www.jiqizhixin.com/article/1611 
0 0 0
本文編譯自 Skymind 的技術博客,作者是深度學習工程師 Alex Black 和 Vyacheslav Kokorin。按照計劃,《Distributed Deep Learning》系列文章一共有三篇,本文是其中的第一篇,後續的文章機器之心還將繼續跟進。

這是關於「神經網絡的分佈訓練」的三篇系列文章中的第一部分。

在第一部分,我們將看到如何在 GPU 上用分佈式計算大大加速深度學習模型的訓練速度,並討論近期該領域上的一些挑戰和近期的研究。同時,我們還要考慮:在什麼時候,神經網絡的分佈式訓練是適合或不適合特定的案例的?

在第二部分,我們將上手式地看看在 Apache Spark 上的 Deeplearning4j 的網絡訓練的實現,並從頭到尾展示一個「如何在實踐中執行訓練」的例子。

最後,在第三部分我們將探索 Deeplearning4j 的 Spark 實現的背後情況,並討論使用 Apache Spark 時的一些涉及到最大化訓練表現的執行和設計挑戰。同時,我們還將看看 Spark 如何與本地的高性能的計算庫和 Deeplearning4j 所使用的堆外內存(off-heap memory)管理互相配合。

介紹

在大型數據集上進行訓練的現代神經網絡架構可以跨廣泛的多種領域獲取可觀的結果,領域涵蓋從語音和圖像認知、自然語言處理、到業界關注的諸如欺詐檢測和推薦系統這樣的應用等各個方面。但是訓練這些神經網絡模型在計算上有嚴格要求。儘管近些年來 GPU 硬件、網絡架構和訓練方法上均取得了重大的進步,但事實是在單一機器上,網絡訓練所需要的時間仍然長得不切實際。幸運的是,我們不僅限於單個機器:大量工作和研究已經使有效的神經網絡分佈式訓練成爲了可能。

我們將從並行式/分佈式的訓練計算這兩種方法開始說起。

download.jpg

在模型並行(model parallelism)中,在分佈式系統中的不同機器分別負責在單個網絡的不同部分計算——例如每層神經網絡可能會被分配到不同的機器。

在數據並行(data parallelism)中,不同的機器有着整個模型的完全拷貝;每個機器只獲得整個數據的不同部分。計算的結果通過某些方法結合起來。

當然,這些方法並不是互相排斥的。想象一個多 GPU 系統的集羣,我們可以對每個機器使用模型並行(將模型分拆到各個 GPU 中),並在機器間進行數據並行。

Synced (141).jpg

儘管在實踐中模型並行可以取得良好的效果,但數據並行毫無爭議是分佈式系統中最適的方法,而且也一直是更多研究的焦點。首先,實現性、容錯性和好的集羣利用率讓數據並行比模型並行更加簡單。在分佈式系統的情況下模型並行是讓人感興趣且的確有一些優點的(諸如對於大模型的可擴展性)。但這裏我們將主要目光放在數據並行上。

數據並行(Data Parallelism)

分佈式訓練中的數據並行方法在每一個 worker machine 上都有一套完整的模型,但分別對訓練數據集的不同子集進行處理。數據並行訓練方法均需要一些整合結果和在各工作器(worker)間同步模型參數的方法。在文中我們將討論一些不同的方法,而這些方法間的基本差異在於:

  • 參數平均 vs. 基於更新(梯度)的方法

  • 同步 vs. 異步的方法

  • 集中式 vs. 分佈式的同步

Deeplearning4j 最近在 Spark 上的實現是同步的參數平均,其中 Spark 驅動器和規約操作(Spark driver and reduction operations)取代了參數服務器。

參數平均(Parameter Averaging)

參數平均化是概念上最爲簡單的數據並行方法。使用參數平均時,訓練按照如下方式執行:

  1. 根據模型配置隨機初始化網絡參數

  2. 將現有的參數的一個副本分配給每一個 worker machine

  3. 在該數據的一個子集上對每一個 worker 進行訓練

  4. 從每一個 worker 的平均參數上設立一個全局參數

  5. 當還需要處理更多數據時,回到第 2 步

第 2 步到第 4 步的過程如下圖所示。在這個圖表中,W 表示神經網絡中的參數(權重,偏置)。下標用作指出參數的版本,以及每個 worker machine 有需求的位置。

Synced (193).jpg

事實上,要證明一個參數平均化的受限版本與單個機器上的訓練在數學上是完全相同的是十分簡單的;這些限制是每個 minibatch 之後的參數平均,沒有更新器(updater)(如沒有動量等——只是通過學習率加倍),而且每個 worker 會處理同樣數量的樣本。對於數學愛好者,證明如下。

假設有一個含有n個 worker 的集羣,其中每個 worker 有m個樣本,總的在平均化中就有nm個樣本。如果我們將所有nm個樣本在同一機器上以學習率α進行處理,那麼我們的權重更新規律滿足如下:

Synced (141).jpg

現在,如果我們換做將 m 個樣本分配到n個 worker 上執行學習(worker 1拿到樣本 1 到 m,worker 2 拿到樣本 m+1 到 2m,以此類推),那麼就有:

Synced (193).jpg

當然,這個結果並不能付諸實踐(平均化每個minibatch和不使用諸如動量或者RMSProp這樣的 updater 都是欠妥的。因爲執行和收斂是分開說明的)。但這提供了第一感覺去思考:爲什麼參數平均可以有好的效果,特別是當參數頻繁平均的時候?

現在,參數平均化在概念上已經十分簡單,但我們也略過了一些複雜的地方。

首先,我們如何執行平均化呢?最爲簡單的方式是在每次迭代後簡單均值化參數。儘管這種方法有效,但我們會發現這樣做的成本會特別高。網絡通信和同步成本會超過我們從額外的機器中所獲得好處。因而,參數平均化的實現通常有多於 1 個的平均化週期(veraging period,就每個 worker 的minibatch數量而言)逐漸執行。然而,如果我們平均化的頻率過低,每個 worker 中的本地參數之間的區別會過大,導致平均化後的模型較差。這裏的直觀知識是:N 個不同局部極小值的均值不能保證是一個局部極小值

Synced (34).JPG

是什麼導致了平均化週期那麼長?這個問題暫時還不能得到決定性的回答。且由於與其他超參數(如學習率、minibatch大小和 worker數量)的相互影響,情況變得更爲複雜。一些該課題上的初步研究(如[8])表明:每10-20個minibatch(每個 worker)排序的平均化週期仍然可以很好的執行。不過模型精確性當然會隨着平均化週期的增加而降低。

與最優化方法相關的附加難題,例如 adagrad,動量和 RMSProp。這些優化方法(在 Deeplearning4j 又稱作更新器(updater))已被證明能在神經網絡訓練的過程中極大地提升收斂性能。然而,這些更新器也有內部狀態(通常一個網絡參數中有 1-2 個狀態值)。我們應該也將這些狀態算入均值嗎?將這些內部更新器狀態平均會造成每個 worker 的更快速的收斂,但代價是比原來總量多 2 倍或者更多的網絡傳輸。有些研究工作也在試圖在參數服務器層面上應用相似的「更新器」機制,而不只是在每一個 worker 上應用。

異步隨機梯度下降

還有一個概念上同參數平均化相似的方法是:「基於更新的」數據並行化(‘update based’ data parallelism)。兩者的基本區別在於:我們不會將參數從 worker 傳遞給參數服務器,而是傳遞更新(例如:梯度柱型的學習率和動量(gradients post learning rate and momentum))。這就得到了這樣形式的更新:

6876896-universe-wallpapers.jpg

其中λ是比例因子(可類比於學習率超參數)

結構上,該方法和參數平均化相似:

Synced (107).jpg

對於訓練神經網絡中數學熟悉的讀者可能會注意到:在參數平均化和基於更新的方法之間有直接的相似之處。如果我們再次定義損失函數爲L,參數向量W能以 i+1 的迭代以學習率 α 進行簡單 SGD 訓練而得到:

Equality_of_Opportunitiy.jpg

其中

Synced (229).jpg

具有 n 個參數

現在,如果我們採取上述的權重更新規則,對於n個執行器讓 λ=1/n,同時再次強調(僅使用學習率爲 α 的 SGD),其更新是:ΔWi,j=α∇L,那麼:

Synced (107).jpg

結果,在參數平均化和基於更新的數據並行間有一個等式,當參數同步更新時(最後一部分是關鍵),這個等式也適用於多個平均化步驟以及其他更新器(不僅僅是簡單的SGD)。

當我們放鬆同步更新的要求時,基於更新的數據並行變得越來越有趣(毫無疑問它更有用)。即在更新∆Wi,j 被計算的時候就應用於參數向量(而不是等待所有 worker 的 N ≥ 1 次迭代)。我們獲得了異步隨機梯度下降算法(async SGD)。async SGD 有兩個主要優點:

  • 首先,我們有潛在可能在整個分佈式系統中獲得更高的通量:worker 可以將更多時間花在執行有用的計算而不是等待參數平均化步驟完成。

  • 其次,worker 有可能可以集成來自其它 worker 的信息(參數更新),這比使用同步(每 N 個步驟)更新更快。

這些優點也不是毫無代價的。通過在參數向量中引入異步更新,我們也引入了一個新問題,也就是過期梯度問題(stale gradient problem)。過期梯度問題很簡單:梯度(更新)的計算需要時間,在一個 worker 完成這些計算並將結果應用於全局參數向量前,這些參數可能已經更新過許多次了。這個問題以下圖展現。

6876896-universe-wallpapers.jpg

一個異步 SGD的樸素實現會造成梯度的過期值(staleness value)很高。例如,Gupta et al. 2015 [3]表明平均梯度的過期值與執行器的數目相等。若有N個執行器,那麼就意味着這些梯度在應用到全局參數向量時會晚 N 個步驟。這在現實世界造成的影響是:高梯度過期值會極大減緩網絡收斂,甚至完全阻止一些配置的收斂。早期的異步 SGD 實現(例如谷歌的DistBelief系統[2])沒有考慮到這個影響,因而導致學習效率很低。

多數的異步隨機梯度下降的變體都保持着相同的基本方法,但採取一些不同的策略來最小化過期梯度所造成的影響,同時試圖保持高的集羣利用率。應該注意的是參數平均化並不是由於算法的同步性本身而受到過期梯度問題的影響。

一些處理處理過期梯度的方法包括:

  • 根據梯度值的延遲度,對於每一個更新的 ∆Wi,j,獨立縮放每一個λ值。

  • 實施「軟」同步規則 ( [9] )。

  • 利用同步去限制延遲度。例如,在 [4] 中所示的系統中,它會在有必要的情況下對較快的學習器進行延遲,以確保整體最大的延遲度小於一個閥值。

這些方法已被證實,能夠改善樸素異步 SGD 算法的收斂情況。其中,最值得注意的是前兩個方法:基於延遲度來縮放更新(延時梯度對參數向量影響較小)以及「軟」同步法。「軟」同步法 [9] 是一個相當簡單的方法——它不立即更新全局參數向量,而是會等待以從 n 個學習器中收集 s 個 ∆W更新(s 是一常數,1 ≤ s ≤ n)。參數的更新規則如:

light-particles.jpg

其中λ(ΔWj)是一個基於延遲度的縮放因子,是一個標量。[9] 提出了

其中 τ 是一個基於延遲度的整數,滿足 τ≥1。同時還有其他方法(見 [6] 中的例子)。若將軟同步法和基於延遲的縮放法結合,則其表現會好於兩者單獨的表現。

注意,若給定 s = 1 以及 λ(·) 爲宜常數,我們得到樸素異步 SGD 算法 [2];相似地,若給定 s=n,我們則會得到另外一個與同步參數平均算法相似但不相同的算法。

分佈式異步梯度下降法

[7] 提出了另一種更爲有趣的備選架構,以執行神經網絡的分佈式訓練。我將這個方法稱作分佈式異步梯度下降法(儘管作者並未使用該術語)。這篇論文在以下兩大方面很有趣:

  1. 在該模型中,沒有中心的參數服務器——取而代之的,是點對點的參數傳輸以對於學習器之間進行更新。

  2. 更新被極大地壓縮了——以至於網絡的通信尺度減小了三個數量級。

6876896-universe-wallpapers.jpg

在一個標準的數據並行執行(使用參數平均或異步 SGD)中,神經網絡的轉存尺寸與參數向量尺寸大小相同(因爲我們要不然傳輸參數向量的複本,要不然每個參數傳輸一個梯度值)。儘管壓縮參數或更新的想法並非完全新穎,但該方法以一種優於傳統的機制(例如應用一個壓縮編碼或轉爲 16 浮點表示)實現了壓縮。

這個架構設計的優勢在於,更新的向量 δi,j 有以下性質:

  1. 稀疏性:在每個向量 δi,j 中,只有部分的梯度值是相互關聯的(也就是其餘的值是被設爲 0 的)——稀疏項使用整數進行索引。

  2. 量化爲一個位:稀疏更新向量每一個分量的值取 +τ 或 −τ。這個 τ 值對向量中的所有分量都相同,因此僅需要一個位就可以區別兩個選項。

  3. 整數索引(即 1 中所提到的用來索引稀疏矩陣)部分地被使用熵編碼,以進一步縮減更新的大小(作者給出了在額外計算的情況下有額外三倍的縮減,儘管該處獲益可能不值得額外的計算)。

此外,考慮到該壓縮方法是有損的,因而原更新向量 ΔWi,j 與壓縮/量化更新的向量 δi,j的差將不被簡單地忽略,而是被儲存在一個殘差向量 rj 中( j代表每次執行)。而殘差向量將被加到原來的更新上,也就是說,每一步我們量化並傳輸一個經過壓縮的 ΔWi,j+rj 並更新合適的 rj。由此,原始的更新向量 ΔWi,j 中的信息被完整的傳輸了並沒有損失。換句話說,(每個參數的)大更新都將被以比小更新更高的速度動態傳輸。

由此產生了兩個問題:一個是,這種方法能多大程度上壓縮神經網絡的參數?另一個是,這種方式的精度如何?答案出乎你意料:它能超出你預料地壓縮,但精度略低於你預期。

如這個在 strom 論文中呈現的例子:一個有約1460萬個參數的模型,經過不同程度壓縮後的情況:

6876896-universe-wallpapers.jpg

更大的 τ 值,將會帶來更大的壓縮率。例如, 當 τ= 15時,對每個數據包,其更新大小僅有4.5KB!但相應的,模型準確率也會因此而下降。

儘管結論很驚人,但該方法也有如下的問題:

  1. Strom在論文中寫道,收斂情況在訓練之初可能出現問題。但使用更少的訓練節點和使用一部分案例好像可以幫助解決該問題。

  2. 壓縮和量化過程需要消耗時間:在對每個數據包處理的過程中,這些過程導致了額外的計算與儲存。

  3. 這一過程引入了需要考的額外的超參數:如何設定 τ值?需要在更新數據的時候使用熵編碼嗎?(儘管參數平均法和異步SGD都引入了額外的超參數。)

最後,就筆者所知,暫時還沒有異步SGD和分佈式異步SGD的實驗比較。

分佈式神經網絡訓練:哪種方法最好?

我們已經看到,有多種方法來訓練分佈式神經網絡,其中每個類型也有不少變體。因此,我們應該在實踐中應該使用哪一個?不幸的是,我們沒有一個很明確的答案。但我們可以給出如下的評判標準,來確定不同方法中最好的那個:

  • 最快的訓練速度(每秒最多或最少可以訓練多少個例子)

  • 在無限樣例下可達到的最大精度

  • 在有限時間下可達到的最大精度

  • 在有限樣例下可達到的最大精度

  • 最大可達到的準確度對曆元的給定數量的

另外,這些問題的答案將可能取決於許多因素,如神經網絡的大小和類型、集羣的硬件性能,使用特徵(如壓縮),以及訓練方式的具體實施方法和配置。

Synced (161).jpg

也就是說,我們能從該研究中總結出如下內容:

同步參數平均法(或等價說,基於同步的更新)在每一次遍歷中的與整體的準確率方面,特別是對很小的平均週期,表現更好。參見 [9] 中所示的」硬同步」結果,或在 N=1 的平均週期下同步平均法在單機訓練上的表現。但是,額外的同步花費意味着這個方法在每次迭代中需要花費更多的時間。也就是說,如 InfiniBand 的更快的神經網絡連接還需要花費很多精力,以使該同步方法具有競爭力(詳見 [5])。但是,甚至在商業硬件上,我們也能見到基於 DL4J 的同步參數的,很好集羣利用。增加壓縮步驟,應該會進一步減少網絡通訊的花費。

也許參數平均(和一般的同步方法)最大的問題,就是所謂的「最慢執行」效應:即同步系統在完成每次迭代之前,需要等待最慢的執行者。因此,當工作機數量增加時,同步系統的表現不會更好。

在實踐中已證明,只要梯度延時被適當處理,異步 SGD 將是一個很好的訓練方案。另外一些方法(如前面所述」軟同步」的方法),根據其所使用的超參數的不同,可被視爲樸素異步 SGD 和同步執行之間的橋樑。

基於集中參數的異步 SGD 實現,可能會引入通信瓶頸(相比之下,同步方法可以利用剪枝或類似算法,能一定程度上避免這方面的溝問題)。將全部的參數分爲 N 等份,使用 N 個參數服務器處理每一份數據,從概念上說,這是一個更爲直接的解決該問題的方法。

最終,分佈式異步 SGD 是一個很有前景的想法,儘管這還需要很多研究才能讓我們不容置疑地推薦它,而非」標準」的異步 SGD。此外,許多在 [7] 中所示的想法(如壓縮、量化等)可以被用於異步 SGD 中,以優化傳統的參數服務器的設置。

該何時使用分佈式深度學習

對每種使用情況,分佈式深度學習往往不都是最好的選擇。

分佈式學習並非廉價——與在單獨的機器上相比,因爲諸如同步、數據與參數的網絡傳輸等問題,分佈式系統往往有一個日常開銷。要使分佈式訓練變得值得,我們需要利用好分佈式系統的計算優勢來抵消這筆開銷。此外,在分佈式訓練上,設定(包括準備與載入訓練數據)及調參都將會變得更爲複雜。因此,我們的建議簡單明瞭:在訓練時間可以接受的情況下,都(不使用分佈式訓練而)在單機上訓練神經網絡。

6876896-universe-wallpapers.jpg

神經網絡的訓練時間因爲這兩種原因而變得很長:網絡的大小非常之大(每次迭代都很費時)及數據量非常之多。通常來說,這兩種情況將同時出現——因爲「大網絡、少數據」或「小網絡、大數據」的情況往往導致欠擬合或過擬合,不能有很好的泛化效果。

在某些情況下,多 GPU 系統應該首先被考慮(如 Deeplearning4j 的 Parallel-Wrapper 系統可以讓神經網絡在單機上輕鬆進行同步訓練)。基於多 GPU 系統對模型進行同步運算對大型網絡也是可行的。

另外一個要考慮的方面是,網絡傳輸(耗時)與計算(耗時)之比。分佈式訓練在網絡傳輸(耗時)與計算(耗時)之比較低時,會比較高效。因爲每層的計算量很少,小的、層數少的網絡並不適用於分佈訓練。有參數共享的網絡(如 CNN 或 RNN)往往適用於分佈式訓練:因爲它們每個參數計算量遠遠高於,如多層感知機或自編碼體系架構的計算量。

Part2 預告:在 Apache Spark 上部署 Deeplearning4j 的深度學習網絡

在我們介紹分佈式深度學習系列文章中,我們將在第三篇的第二部分仔細探討 Deeplearning4j 的機遇 Apache Spark 的參數平均法的實現,並通過一個例子來演示如何在 Spark 集羣上來訓練神經網絡。

參考文獻

[1]  Kai Chen and Qiang Huo. Scalable training of deep learning machines by incremental block training with intra-block parallel optimization and blockwise model-update filtering. In 2016 IEEE International Conference on Acoustics, Speech and Signal Processing (ICASSP), pages 5880–5884. IEEE, 2016.

[2]  Jeffrey Dean, Greg Corrado, Rajat Monga, Kai Chen, Matthieu Devin, Mark Mao, Andrew Senior, Paul Tucker, Ke Yang, Quoc V Le, et al. Large scale distributed deep networks. In Advances in Neural Information Processing Systems, pages 1223–1231, 2012.

[3]  Suyog Gupta, Wei Zhang, and Josh Milthrope. Model accuracy and runtime tradeoff in distributed deep learning. arXiv preprint arXiv:1509.04210, 2015.

[4]  Qirong Ho, James Cipar, Henggang Cui, Seunghak Lee, Jin Kyu Kim, Phillip B. Gibbons, Garth A Gibson, Greg Ganger, and Eric P Xing. More effective distributed ml via a stale synchronous parallel parameter server. In C. J. C. Burges, L. Bottou, M. Welling, Z. Ghahramani, and K. Q. Weinberger, editors,Advances in Neural Information Processing Systems 26, pages 1223–1231. Curran Associates, Inc., 2013.

[5]  Forrest N Iandola, Khalid Ashraf, Mattthew W Moskewicz, and Kurt Keutzer. Firecaffe: near-linear acceleration of deep neural network training on compute clusters. arXiv preprint arXiv:1511.00175, 2015.

[6]  Augustus Odena. Faster asynchronous sgd. arXiv preprint arXiv:1601.04033, 2016.

[7]  Nikko Strom. Scalable distributed dnn training using commodity gpu cloud computing. InSixteenth Annual Conference of the International Speech Communication Association, 2015.http://nikkostrom.com/publications/interspeech2015/strom_interspeech2015.pdf.

[8]  Hang Su and Haoyu Chen. Experiments on parallel training of deep neural network using model averaging. arXiv preprint arXiv:1507.01239, 2015.

[9]  Wei Zhang, Suyog Gupta, Xiangru Lian, and Ji Liu. Staleness-aware async-sgd for distributed deep learning. IJCAI, 2016.

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章