深度学习优化器
-
神经网络模型的学习方法(优化器)一般使用梯度下降算法:
- 令网络模型的损失函数为: J ( θ ) J(θ) J(θ);其中 θ θ θ是整个模型需要学习的参数。
- 然后将参数 θ θ θ向负梯度方向更新: θ t = θ t − 1 − η ∇ J ( θ ) θ_t=θ_{t-1}-η∇J(θ) θt=θt−1−η∇J(θ); η η η为学习率表明梯度更新的步伐大小
-
可以看出深度学习优化器的两个核心:梯度与学习率,前者决定参数更新的方向后者决定参数更新程度
-
深度学习优化器之所以采用梯度下降算法是因为,对于高维的函数其更高阶导的计算复杂度大,应用到深度学习的优化中不实际。
-
深度学习的优化器种类:
- 第一类:优化过程中学习率 η η η不受梯度 ∇ J ( θ ) ∇J(θ) ∇J(θ)影响:
- SGD(随机梯度下降法)系列:一般的SGD,带Momentum的SGD,带Nesterov的SGD
- 第二类:优化过程中学习率 η η η随着梯度 ∇ J ( θ ) ∇J(θ) ∇J(θ)自适应的改变。
- 常见的包:Adagrad、Adadelta、RMSprop、Adam、Nadam
- 第一类:优化过程中学习率 η η η不受梯度 ∇ J ( θ ) ∇J(θ) ∇J(θ)影响:
SGD:
-
标准的梯度下降算法(GD):目标函数 J ( θ ) J(θ) J(θ)是整个样本集损失函数的累加: J ( θ ) = ∑ i = 1 T L o s s i J(θ)=∑_{i=1}^TLoss_i J(θ)=∑i=1TLossi
-
标准随机梯度下降算法(SGD): J ( θ ) = L o s s i J(θ)=Loss_i J(θ)=Lossi(一个样本的损失函数)
-
小批量随机梯度下降算法(mini-batch gradient descent): J ( θ ) = ∑ i = 1 b a t c h L o s s i J(θ)=∑_{i=1}^{batch}Loss_i J(θ)=∑i=1batchLossi
-
一般说SGD都指的是 mini-batch gradient descent:
- 首先对当前batch中样本的loss进行进行累加得到目标函数: J ( θ ) = ∑ i = 1 b a t c h L o s s i J(θ)=∑_{i=1}^{batch}Loss_i J(θ)=i=1∑batchLossi
- 参数更新公式: θ t = θ t − 1 − η ∇ J ( θ ) θ_t=θ_{t-1}-η∇J(θ) θt=θt−1−η∇J(θ)
- SGD完全依赖于当前batch的梯度,所以 η η η可理解为允许当前batch的梯度多大程度影响参数更新。
-
缺点:
- 选择合适的固定的学习率比较困难。对于稀疏(不经常出现)的数据或者特征,有时我们可能想更新快一些,对于常出现的特征更新慢一些,这时候SGD就不太能满足要求了
- SGD容易收敛到局部最优
Momentum:
- SGD在遇到沟壑时容易陷入震荡。为此其引入动量 Momentum,加速 SGD 在正确方向的下降并抑制震荡。
- 梯度公式: m t = γ m t − 1 + η g t m_t=γm_{t-1}+ηg_t mt=γmt−1+ηgt g t = ∇ J ( θ ) g_t=∇J(θ) gt=∇J(θ) m t − 1 m_{t-1} mt−1被称为前面更新步骤的动量,一般 γ = 0.9 γ=0.9 γ=0.9
- 参数更新公式: θ = θ − m t θ=θ-m_t θ=θ−mt
- 由公式可知参数更新方向不仅由当前的梯度决定,也与此前累积的下降方向有关
- 这使得参数中那些梯度方向变化不大的维度可以加速更新,并减少梯度方向变化较大的维度上的更新幅度。由此产生了加速收敛和减小震荡的效果。
- SGD与SGDM的对比图
Nesterov Accelerated Gradient:
- 梯度公式: g t = ∇ J ( θ − γ m t − 1 ) g_t=∇J(θ-γm_{t-1} ) gt=∇J(θ−γmt−1) m t = γ m t − 1 + η g t m_t=γm_{t-1}+ηg_t mt=γmt−1+ηgt
- 参数更新公式: θ = θ − m t θ=θ-m_t θ=θ−mt m t m_t mt被称为一阶动量
- 更新图片:
- 图中SGD-M的步长计算了当前梯度(短蓝向量)和动量项 (长蓝向量);NAG先按公式 θ − μ m t − 1 θ-μm_{t-1} θ−μmt−1计算出下一时刻的近似位置(棕向量),并根据该未来位置计算梯度(红向量),然后使用和SGD-M中相同的方式计算NAG真实步长(绿向量)。
- 这种计算梯度的方式可以使算法更好的预测未来,提前调整更新速率
- 算法能够在目标函数有增高趋势之前,减缓更新速率。NAG相当于在更新时做一个校正,避免前进太快,同时提高灵敏度
Adagrad:
- SGD、SGD-M 和 NAG 均是以相同的学习率去更新参数 θ θ θ的各个分量。而深度学习模型中往往涉及大量的参数,不同参数的更新频率往往有所区别。对于更新不频繁的参数(典型例子:更新 word embedding中的低频词),我们希望单次步长更大,多学习一些知识;对于更新频繁的参数,我们则希望步长较小,使得学习到的参数更稳定,不至于被单个样本影响太多
- 引入二阶动量: v t = d i a g ( ∑ i t g i , 1 2 , ∑ i t g i , 2 2 , … , ∑ i t g i , d 2 ) v_t=diag(∑_i^tg_{i,1}^2 ,∑_i^tg_{i,2}^2 ,…,∑_i^tg_{i,d}^2 ) vt=diag(i∑tgi,12,i∑tgi,22,…,i∑tgi,d2) d d d为参数 θ θ θ的维度, v t ∈ R ( d × d ) v_t∈R^(d×d) v