神经网络优化方法

从最优化的角度来看,主要有一阶和二阶两类优化方案,那么从最简单的开始:


  1. Gradient Descent
while True:
  weights_grad = evaluate_gradient(loss_fun, data, weights)
  weights += - step_size*weightes_grad

缺点:

  • 计算量过大
  • 对于非凸函数不能保证全局最优
  1. SGD(Stochastic Gradient Descent)
while True:
  data_batch = sample_training_data(data,256)
  weights_grad = evaluate_gradient(loss_fun, data_batch, weights)
  weights += - step_size * weighted_grad

注意此处代码给出的是mini-batch 的SGD,还有一种是针对每个输入数据的SGD(batch_size=1),该方法在优化过程中会有比较明显的震荡。
缺点:

  • 可能出现的高方差使得收敛速度慢,稳定性差
  • 需要选取合适的学习率
  • 没有解决非凸函数问题
  1. SGD+Momentum
vx = 0
while True:
  dx = compute_gradient(x)
  ### 通常rho取0.9或者0.99
  vx = rho * vx +dx
  x += - learning_rate * vx
神经网络优化方法_第1张图片

优点:

  • 能够遏制动荡
  • 可以越过局部最小点和鞍点
    缺点:
  • 可能因为高动量而越过最小值
  1. Nesterov
vx = 0
while True:
  dx = compute_gradient(x)
  old_v = v
  v = rho * v - learning_rate * dx
  x += - rho* old_v + (1+rho)* v

原本的数学公式应当写成:


神经网络优化方法_第2张图片

不过括号中的导数不便于计算,因此经过化简得到上述结果。
其原理如下:为了改进动量方法的越过最小点问题,需要提前看一点。


神经网络优化方法_第3张图片
  1. AdaGrad
grad_squared = 0
while True:
  dx = compute_gradient(x)
  grad_squared += dx * dx
  x -= learning_rate * dx / (np.sqrt(grad_squared) + 1e-7)
  1. RMSprop
grad_squared = 0
while True:
  dx = computer_gradient(x)
  grad_squared = decay_rate * grad_squared + (1-decay_rate) * dx *dx
  x -= learning_rate * dx / (np.sqrt(grad_squared) + 1e-7)
  1. Adam
first_moment = 0
second_moment = 0
for t in range(1, num_iterations):
  dx = compute_gradient(x)
  first_moment = beta1 * first_moment + (1-beta1) * dx
  second_moment = beta2 * second_moment + (1-beta2)*dx*dx
  # 为了修正一开始 first_mometn和 second_moment从0开始累积,有了以下两项
  first_unbias = first_moment / (1 - beta1 ** t)
  second_unbias = second_moment / (1 - beta2 **t)
  x -= learning_rate * first_unbias / (np.sqrt(second_unbias) + 1e-7)

Reference:

  1. http://cs231n.stanford.edu/slides/2017/cs231n_2017_lecture3.pdf
  2. http://cs231n.stanford.edu/slides/2017/cs231n_2017_lecture7.pdf
  3. https://zhuanlan.zhihu.com/p/27449596

你可能感兴趣的:(神经网络优化方法)