from: https://www.jianshu.com/p/aebcaf8af76e
基于随機梯度下降(SGD)的優化算法在科研和工程的很多領域裡都是極其核心的。很多理論或工程問題都可以轉化為對目标函數進行最小化的數學問題。
按吳恩達老師所說的,梯度下降(Gradient Descent)就好比一個人想從高山上奔跑到山谷最低點,用最快的方式(steepest)奔向最低的位置(minimum)。
SGD基本公式

動量(Momentum)
參考連結:https://distill.pub/2017/momentum/
基本的mini-batch SGD優化算法在深度學習取得很多不錯的成績。然而也存在一些問題需解決:
1. 選擇恰當的初始學習率很困難。
2. 學習率調整政策受限于預先指定的調整規則。
3. 相同的學習率被應用于各個參數。
4. 高度非凸的誤差函數的優化過程,如何避免陷入大量的局部次優解或鞍點。
自适應優化
AdaGrad
針對簡單的SGD及Momentum存在的問題,2011年John Duchi等釋出了AdaGrad優化算法(Adaptive Gradient,自适應梯度),它能夠對每個不同的參數調整不同的學習率,對頻繁變化的參數以更小的步長進行更新,而稀疏的參數以更大的步長進行更新。
公式:
gt表示第t時間步的梯度(向量,包含各個參數對應的偏導數,gt,i表示第i個參數t時刻偏導數)
gt2表示第t時間步的梯度平方(向量,由gt各元素自己進行平方運算所得,即Element-wise)
與SGD的核心差別在于計算更新步長時,增加了分母:梯度平方累積和的平方根。此項能夠累積各個參數gt,i的曆史梯度平方,頻繁更新的梯度,則累積的分母項逐漸偏大,那麼更新的步長(stepsize)相對就會變小,而稀疏的梯度,則導緻累積的分母項中對應值比較小,那麼更新的步長則相對比較大。
AdaGrad能夠自動為不同參數适應不同的學習率(平方根的分母項相當于對學習率α進進行了自動調整,然後再乘以本次梯度),大多數的架構實作采用預設學習率α=0.01即可完成比較好的收斂。
優勢:在資料分布稀疏的場景,能更好利用稀疏梯度的資訊,比标準的SGD算法更有效地收斂。
缺點:主要缺陷來自分母項的對梯度平方不斷累積,随之時間步地增加,分母項越來越大,最終導緻學習率收縮到太小無法進行有效更新。
RMSProp
RMSProp是Geoffrey Hinton教授在教案中提到的算法,結合梯度平方的指數移動平均數來調節學習率的變化。能夠在不穩定(Non-Stationary)的目标函數情況下進行很好地收斂。
Hinton教授講述RMSProp算法的材料:
http://www.cs.toronto.edu/~tijmen/csc321/slides/lecture_slides_lec6.pdf
計算t時間步的梯度:
計算梯度平方的指數移動平均數(Exponential Moving Average),γ是遺忘因子(或稱為指數衰減率),依據經驗,預設設定為0.9。
梯度更新時候,與AdaGrad類似,隻是更新的梯度平方的期望(指數移動均值),其中ε=10^-8,避免除數為0。預設學習率α=0.001。
優勢:能夠克服AdaGrad梯度急劇減小的問題,在很多應用中都展示出優秀的學習率自适應能力。尤其在不穩定(Non-Stationary)的目标函數下,比基本的SGD、Momentum、AdaGrad表現更良好。
Adam優化器
2014年12月,Kingma和Lei Ba兩位學者提出了Adam優化器,結合AdaGrad和RMSProp兩種優化算法的優點。對梯度的一階矩估計(First Moment Estimation,即梯度的均值)和二階矩估計(Second
Moment Estimation,即梯度的未中心化的方差)進行綜合考慮,計算出更新步長。
主要包含以下幾個顯著的優點:
1. 實作簡單,計算高效,對記憶體需求少
2. 參數的更新不受梯度的伸縮變換影響
3. 超參數具有很好的解釋性,且通常無需調整或僅需很少的微調
4. 更新的步長能夠被限制在大緻的範圍内(初始學習率)
5. 能自然地實作步長退火過程(自動調整學習率)
6. 很适合應用于大規模的資料及參數的場景
7. 适用于不穩定目标函數
8. 适用于梯度稀疏或梯度存在很大噪聲的問題
綜合Adam在很多情況下算作預設工作性能比較優秀的優化器。
Adam實作原理
算法僞代碼:
Adam更新規則
計算t時間步的梯度:
首先,計算梯度的指數移動平均數,m0 初始化為0。
類似于Momentum算法,綜合考慮之前時間步的梯度動量。
β1 系數為指數衰減率,控制權重配置設定(動量與目前梯度),通常取接近于1的值。
預設為0.9
下圖簡單展示出時間步1~20時,各個時間步的梯度随着時間的累積占比情況。
其次,計算梯度平方的指數移動平均數,v0初始化為0。
β2 系數為指數衰減率,控制之前的梯度平方的影響情況。
類似于RMSProp算法,對梯度平方進行權重均值。
預設為0.999
第三,由于m0初始化為0,會導緻mt偏向于0,尤其在訓練初期階段。
是以,此處需要對梯度均值mt進行偏差糾正,降低偏差對訓練初期的影響。
第四,與m0 類似,因為v0初始化為0導緻訓練初始階段vt偏向0,對其進行糾正。
第五,更新參數,初始的學習率α乘以梯度均值與梯度方差的平方根之比。
其中預設學習率α=0.001
ε=10^-8,避免除數變為0。
由表達式可以看出,對更新的步長計算,能夠從梯度均值及梯度平方兩個角度進行自适應地調節,而不是直接由目前梯度決定。
Adam代碼實作
算法思路很清晰,實作比較直覺:
代碼位址:https://github.com/dream-catcher/learning_blogs/blob/master/Adam_Optimizer/adam_optimizer.py
Adam可視化
notebook試驗位址:https://github.com/dream-catcher/learning_blogs/tree/master/Adam_Optimizer
Adam缺陷及改進
雖然Adam算法目前成為主流的優化算法,不過在很多領域裡(如計算機視覺的對象識别、NLP中的機器翻譯)的最佳成果仍然是使用帶動量(Momentum)的SGD來擷取到的。Wilson 等人的論文結果顯示,在對象識别、字元級别模組化、文法成分分析等方面,自适應學習率方法(包括AdaGrad、AdaDelta、RMSProp、Adam等)通常比Momentum算法效果更差。
針對Adam等自适應學習率方法的問題,主要兩個方面的改進:
1、解耦權重衰減
在每次更新梯度時,同時對其進行衰減(衰減系數w略小于1),避免産生過大的參數。
在Adam優化過程中,增加參數權重衰減項。解耦學習率和權重衰減兩個超參數,能單獨調試優化兩個參數。
參考連結:http://ruder.io/deep-learning-optimization-2017/index.html
2、修正指數移動均值
最近的幾篇論文顯示較低的[if !msEquation][endif](如0.99或0.9)能夠獲得比預設值0.999更佳的結果,暗示出指數移動均值本身可能也包含了缺陷。例如在訓練過程中,某個mini-batch出現比較大資訊量的梯度資訊,但由于這類mini-batch出現頻次很少,而指數移動均值會減弱他們的作用(因為目前梯度權重及目前梯度的平方的權重,權重都比較小),導緻在這種場景下收斂比較差。
https://openreview.net/pdf?id=ryQu7f-RZ
論文作者提出Adam的變形算法AMSGrad。
AMSGrad 使用最大的來更新梯度,而不像Adam算法中采用曆史的指數移動均值來實作。作者在小批量資料集及CIFAR-10上觀察到比Adam更佳的效果。
參考資料
http://ruder.io/optimizing-gradient-descent/
http://ruder.io/deep-learning-optimization-2017/index.html
作者:Emerson_G
連結:https://www.jianshu.com/p/aebcaf8af76e
來源:簡書