cs231n lecture 16 7.1笔记--更好的优化

last time:

  1. activation function:sigmoid, tanh, relu, leacky relu, maxout, ELU
  2. weight initialization:Xavier初始化,MSRA初始化。初始化过小无法学习,过大梯度消失。
  3. data preprocessing:中心化,归一化。好处是让loss对参数值中的小扰动不那么敏感。
  4. batch normalization
  5. babysitting learning
  6. hyperparameter search
    1. grid search,random search, coarse to fine search(粗细粒交叉搜索)

通常学习率 > 正则化、学习率衰减、模型size。

卡在局部最优解的问题,在直观上是存在的但实际并不会。

SGD的问题:

1. very slow progress along shallow dimension, jitter along steep direction

2. 会卡在局部最小点和鞍点

3. stochastic

 

解决:SGD + Momentum

rho gives friction, and typically rho =0.9 or 0.99(也可以理解成最近梯度平均的平滑移动)

=> nesterov momentum, 据说在凸优化问题上效果不错。

momentum中的速度不是超参数,初始化设置为0即可。

sgd + momentum能够帮助度过sharp minima,如果遇到较宽泛的minima呢?老师说,一来这样的问题出现往往预示了过拟合,所以扩大数据集有用。二来甚至希望达到一个平缓的minima,这样能够更好地训练其泛化能力

AdaGrad

grad_squared = 0

while True:

dx = compute_gradient(x)

grad_squared += dx * dx

x -= learning_rate * dx / (np.sqrt(grad_squared) + 1e-7)

adagrad能够使x在变化率高的轴上减速,变化小的轴上加速,从而缓解jitter。

adagrad随着时间增加,步长会逐渐缩短,这在凸函数优化问题上有利于收敛,但其他问题则得不偿失。

 

=> RMSProp

grad_squared = 0

while True:

dx = compute_gradient(x)

grad_squared = decay_rate * grad_squared + (1 - decay_rate) * dx * dx

x -= learning_rate * dx / (np.sqrt(grad_squared) + 1e-7)

decay_rate通常取0.9之类。这样的好处是依然能够使训练在较快的方向渐缓,较慢的方向增快。并且不像adagrad那样容易被卡住。

 

Adam(full form)

 

因为效果优异,基本就是默认算法了。beta1 = 0.9, beta2 = 0.999, and learning_rate = 1e-3 or 5e-4是开始新模型时最常用的设定。

但这些算法都难以解决loss等高线如墨西哥卷形状不沿着坐标轴对齐,那么这些算法就是能够提供压缩但无法扭正。

 

learning rate decay over time!

带动向量的SGD很常用lr decay,但是Adam很少用。而且因为lr decay是二阶超参数,所以一开始最好不用,而是观察原来情况后再选择使用。

事实上,也有二阶优化的思路。一阶梯度带来的下降可能不如二阶函数拟合的到位

=> Newton parameter

这个算法甚至降低了对learning_rate的需要。但因为牛顿法中需要求矩阵的逆,往往不能计算,所以也有拟牛顿法,去低阶拟近hessian

L-BFGS是一个二阶逼近的求导器。二阶的思路虽好,但在深度学习中可能不太常用。

 

此前谈论的最优化问题只是针对train data,如果想提升泛化性能

=> Model Ensembles(虽然没有什么吊提升,但是每次提升程度都很稳)