深度学习之参数优化方法
2018-01-03 20:37
183 查看
优化问题:给定目标函数f(x),我们需要找到一组参数x,使得f(x)的值最小
optimizer = tf.train.GradientDescentOptimizer(learning_rate=self.learning_rate)
直接进行优化
x += - learning_rate * dx
对于训练数据集,我们首先将其分成n个batch,每个batch包含m个样本。我们每次更新都利用一个batch的数据,而非整个训练集。即:
好处在于:
当训练数据太多时,利用整个数据集更新往往时间上不显示。batch的方法可以减少机器的压力,并且可以更快地收敛
当训练集有很多冗余时(类似的样本出现多次),batch方法收敛更快。以一个极端情况为例,若训练集前一半和后一半梯度相同。那么如果前一半作为一个batch,后一半作为另一个batch,那么在一次遍历训练集时,batch的方法向最优解前进两个step,而整体的方法只前进一个step
optimizer = tf.train.MomentumOptimizer(lr,
0.9)
直接进行优化
v = mu * v - learning_rate * dx # integrate velocity
x += v # integrate position
SGD方法的一个缺点是,其更新方向完全依赖于当前的batch,因而其更新十分不稳定。解决这一问题的一个简单的做法便是引入momentum。
momentum即动量,它模拟的是物体运动时的惯性,即更新的时候在一定程度上保留之前更新的方向,同时利用当前batch的梯度微调最终的更新方向。这样一来,可以在一定程度上增加稳定性,从而学习地更快,并且还有一定摆脱局部最优的能力:
其中一般的,v初始为0,mu是优化参数,一般初始化参数为0.9,当使用交叉验证的时候,参数mu一般设置成[0.5,0.9,0.95,0.99],在开始训练的时候,梯度下降较快,可以设置mu为0.5,在一段时间后逐渐变慢了,mu可以设置为0.9、0.99。也正是因为有了“惯性”,这个比SGD会稳定一些。
v = mu * v - learning_rate * dx_ahead
x += v
这是Momentum update的改进版,之前我们采用
optimizer = tf.train.AdagradientOptimizer(learning_rate=self.learning_rate)
直接进行优化
cache
+= dx**2
x += - learning_rate * dx / (np.sqrt(cache) + eps)
上面提到的方法对于所有参数都使用了同一个更新速率。但是同一个更新速率不一定适合所有参数。比如有的参数可能已经到了仅需要微调的阶段,但又有些参数由于对应样本少等原因,还需要较大幅度的调动。Adagrad就是针对这一问题提出的,自适应地为各个参数分配不同学习率的算法。
其中gt 同样是当前的梯度,连加和开根号都是元素级别的运算。eta是初始学习率,由于之后会自动调整学习率,所以初始值就没有之前的算法那样重要了。eps是一个平滑的过程,取值通常在(10^-4~10^-8
之间)
其含义是,对于每个参数,随着其更新的总距离增多,其学习速率也随之变慢。
Adagrad中chche累加的原因是在后期作为惩罚项,这样的话学习率越来越小,符合在最后接近收敛的时候,步长越来越小的要求。
前期gt较小的时候,chche累加 regularizer较大,能够放大梯度
后期gt较大的时候,chche累加regularizer较小,能够约束梯度
适合处理稀疏梯度
optimizer = tf.train.RMSPropOptimizer(0.001, 0.9)
直接进行优化
cache=
decay_rate*cache+
(1-
decay_rate)* dx**2
x+=-
learning_rate* dx/
(np.sqrt(cache)+
eps)
decay_rate是一个超参数,常用的值是[0.9,0.99,0.999]。其中x+=和Adagrad中是一样的,但是cache变量是不同的。
因此,RMSProp仍然是基于梯度的大小来对每个权重的学习率进行修改,这同样效果不错。
但是和Adagrad不同,其更新不会让学习率单调变小。
m = beta1*m + (1-beta1)dx
v = beta2*v + (1-beta2)
v = beta2*v
+ (1-beta2)(dx**2)
x += - learning_rate
* m / (np.sqrt(v) + eps)
有点像RMSProp+momentum
参考来自:
http://blog.csdn.net/bea_tree/article/details/51523733#411-vanilla-update http://blog.csdn.net/luo123n/article/details/48239963
1.Vanilla update
tensorflow实现optimizer = tf.train.GradientDescentOptimizer(learning_rate=self.learning_rate)
直接进行优化
train_op = optimizer.minimize(loss)
x += - learning_rate * dx
对于训练数据集,我们首先将其分成n个batch,每个batch包含m个样本。我们每次更新都利用一个batch的数据,而非整个训练集。即:
好处在于:
当训练数据太多时,利用整个数据集更新往往时间上不显示。batch的方法可以减少机器的压力,并且可以更快地收敛
当训练集有很多冗余时(类似的样本出现多次),batch方法收敛更快。以一个极端情况为例,若训练集前一半和后一半梯度相同。那么如果前一半作为一个batch,后一半作为另一个batch,那么在一次遍历训练集时,batch的方法向最优解前进两个step,而整体的方法只前进一个step
2.Momentum update动量更新
tensorflow实现optimizer = tf.train.MomentumOptimizer(lr,
0.9)
直接进行优化
train_op = optimizer.minimize(loss)
v = mu * v - learning_rate * dx # integrate velocity
x += v # integrate position
SGD方法的一个缺点是,其更新方向完全依赖于当前的batch,因而其更新十分不稳定。解决这一问题的一个简单的做法便是引入momentum。
momentum即动量,它模拟的是物体运动时的惯性,即更新的时候在一定程度上保留之前更新的方向,同时利用当前batch的梯度微调最终的更新方向。这样一来,可以在一定程度上增加稳定性,从而学习地更快,并且还有一定摆脱局部最优的能力:
其中一般的,v初始为0,mu是优化参数,一般初始化参数为0.9,当使用交叉验证的时候,参数mu一般设置成[0.5,0.9,0.95,0.99],在开始训练的时候,梯度下降较快,可以设置mu为0.5,在一段时间后逐渐变慢了,mu可以设置为0.9、0.99。也正是因为有了“惯性”,这个比SGD会稳定一些。
3.Nesterov Momentum
x_ahead = x + mu * vv = mu * v - learning_rate * dx_ahead
x += v
这是Momentum update的改进版,之前我们采用
v = mu * v - learning_rate * dx的方法计算增量,其中的dx还是当前的x,但是我们已经知道了,下一刻的惯性将会带我们去的位置,所以现在我们要用加了mu*v之后的x,来更新位置(在更新后的位置而不是在原点求解梯度),下面的图很形象:
4.Adagrad
tensorflow实现optimizer = tf.train.AdagradientOptimizer(learning_rate=self.learning_rate)
直接进行优化
train_op = optimizer.minimize(loss)
cache
+= dx**2
x += - learning_rate * dx / (np.sqrt(cache) + eps)
上面提到的方法对于所有参数都使用了同一个更新速率。但是同一个更新速率不一定适合所有参数。比如有的参数可能已经到了仅需要微调的阶段,但又有些参数由于对应样本少等原因,还需要较大幅度的调动。Adagrad就是针对这一问题提出的,自适应地为各个参数分配不同学习率的算法。
其中gt 同样是当前的梯度,连加和开根号都是元素级别的运算。eta是初始学习率,由于之后会自动调整学习率,所以初始值就没有之前的算法那样重要了。eps是一个平滑的过程,取值通常在(10^-4~10^-8
之间)
其含义是,对于每个参数,随着其更新的总距离增多,其学习速率也随之变慢。
Adagrad中chche累加的原因是在后期作为惩罚项,这样的话学习率越来越小,符合在最后接近收敛的时候,步长越来越小的要求。
前期gt较小的时候,chche累加 regularizer较大,能够放大梯度
后期gt较大的时候,chche累加regularizer较小,能够约束梯度
适合处理稀疏梯度
5.RMSprop
tensorflow实现optimizer = tf.train.RMSPropOptimizer(0.001, 0.9)
直接进行优化
train_op = optimizer.minimize(loss)
cache=
decay_rate*cache+
(1-
decay_rate)* dx**2
x+=-
learning_rate* dx/
(np.sqrt(cache)+
eps)
decay_rate是一个超参数,常用的值是[0.9,0.99,0.999]。其中x+=和Adagrad中是一样的,但是cache变量是不同的。
因此,RMSProp仍然是基于梯度的大小来对每个权重的学习率进行修改,这同样效果不错。
但是和Adagrad不同,其更新不会让学习率单调变小。
6.Adam
tensorflow函数:class tf.train.AdamOptimizer
__init__(learning_rate=0.001, beta1=0.9, beta2=0.999, epsilon=1e-08, use_locking=False, name='Adam')
直接进行优化
train_op = optimizer.minimize(loss)
m = beta1*m + (1-beta1)dx
v = beta2*v + (1-beta2)
v = beta2*v
+ (1-beta2)(dx**2)
x += - learning_rate
* m / (np.sqrt(v) + eps)
有点像RMSProp+momentum
参考来自:
http://blog.csdn.net/bea_tree/article/details/51523733#411-vanilla-update http://blog.csdn.net/luo123n/article/details/48239963
相关文章推荐
- 深度学习优化方法
- 深度学习之(十一)Deep learning中的优化方法:随机梯度下降、受限的BFGS、共轭梯度法
- 深度学习——sgd等优化方法比较
- 深度学习最全优化方法总结比较(SGD,Adagrad,Adadelta,Adam,Adamax,Nadam)
- 转:深度学习笔记:优化方法总结(BGD,SGD,Momentum,AdaGrad,RMSProp,Adam)
- 深度学习优化方法比较
- 深度学习最全优化方法总结比较(SGD,Adagrad,Adadelta,Adam,Adamax,Nadam)
- 深度学习最全优化方法总结比较(SGD,Adagrad,Adadelta,Adam,Adamax,Nadam)
- 如何使用网格搜索来优化深度学习模型中的超参数(Keras)
- 深度学习最全优化方法总结比较(SGD,Adagrad,Adadelta,Adam,Adamax,Nadam)
- 【深度学习】极值优化方法总结比较(SGD,Adagrad,Adadelta,Adam,Adamax,Nadam)
- 深度学习基础(九)—— 深度学习中的优化方法
- 深度学习最全优化方法总结比较(SGD,Adagrad,Adadelta,Adam,Adamax,Nadam)
- 深度学习优化方法总结
- 浅析深度学习中优化方法
- 深度学习最全优化方法总结比较(SGD,Adagrad,Adadelta,Adam,Adamax,Nadam)
- 深度学习 训练优化方法讲述
- 深度学习最全优化方法总结比较(SGD,Adagrad,Adadelta,Adam,Adamax,Nadam)
- 浅析深度学习中优化方法
- 深度学习最全优化方法总结比较(SGD,Adagrad,Adadelta,Adam,Adamax,Nadam)