在训练机器学习模型寻找最优函数时,梯度下降(Gradient Descent)是最常用的优化(optimization)方法。在给定一组初始参数 θ 0 \theta^0 θ0时,梯度下降算法能够顺着损失函数下降最快的方向逐步逼近最低点,也就是最佳参数 θ ∗ \theta^* θ∗的位置。 那梯度下降算法为什么work呢?为什么梯度的反方向就是损失函数下降最快的方向呢?
梯度下降算法解释
首先回顾一下梯度下降算法是如何工作的,我们的目标是找到
θ
∗
\theta^*
θ∗:
θ
∗
=
a
r
g
min
θ
L
(
θ
)
\theta^*=arg\min_\theta L(\theta)
θ∗=argθminL(θ)
其中 L L L是损失函数,梯度下降算法步骤如下:
- 随机选取一组初始参数 θ 0 \theta^0 θ0。
- 计算损失函数在该点的偏导数 ∇ L ( θ n − 1 ) \nabla L(\theta^{n-1}) ∇L(θn−1),也就是梯度。
- 更新参数 θ n = θ n − 1 − η ∇ L ( θ n − 1 ) \theta^n=\theta^{n-1}-\eta\nabla L(\theta^{n-1}) θn=θn−1−η∇L(θn−1)。
- 重复2,3步骤,直至梯度不再下降(小于某个阈值范围)。
上面第3步中可以看到,每次我们顺着梯度的反方向更新
θ
\theta
θ,其中
η
\eta
η是学习速率,代表了每次更新的步伐大小。在只含有两个未知参数时,梯度下降的直观过程如下图:
下面根据李宏毅课程的思路对梯度下降的原理进行解释。同样假设只包含两个参数
θ
1
\theta^1
θ1,
θ
2
\theta^2
θ2。随机给定一个初始点,在“目之所及”的范围内寻找损失函数下降最快的方向,如下图
θ
0
\theta^0
θ0是随机给定的初始点,红色圆圈是“目之所及”的范围,现在的关键是如何找到圆圈范围内下降最快的方向,由泰勒展示(Taylor Series):当函数
h
(
x
)
h(x)
h(x)在
x
=
x
0
x=x_0
x=x0处是可微的,那么
h
(
x
)
h(x)
h(x)可以写成
h
(
x
)
=
∑
k
=
0
∞
h
(
k
)
(
x
0
)
k
!
(
x
−
x
0
)
k
=
h
(
x
0
)
+
h
′
(
x
0
)
(
x
−
x
0
)
+
h
′
′
(
x
0
)
2
!
(
x
−
x
0
)
2
+
⋯
\begin{aligned} h(x) =& \sum_{k=0}^\infty\frac{h^{(k)}(x_0)}{k!}(x-x_0)^k\\ =& h(x_0)+h^{'}(x_0)(x-x_0)+\frac{h^{''}(x_0)}{2!}(x-x_0)^2+\cdots \end{aligned}
h(x)==k=0∑∞k!h(k)(x0)(x−x0)kh(x0)+h′(x0)(x−x0)+2!h′′(x0)(x−x0)2+⋯
当
x
x
x非常接近
x
0
x_0
x0时,上式中的平方项等更高次项的值将无限接近于0,此时
h
(
x
)
h(x)
h(x)可以约等于
h
(
x
)
≈
h
(
x
0
)
+
h
′
(
x
0
)
(
x
−
x
0
)
h(x)\approx h(x_0)+h^{'}(x_0)(x-x_0)
h(x)≈h(x0)+h′(x0)(x−x0)
多变量泰勒展示同样成立,只需对各个变量分别求偏导数
h
(
x
,
y
)
≈
h
(
x
0
,
y
0
)
+
∂
h
(
x
0
,
y
0
)
∂
x
(
x
−
x
0
)
+
∂
h
(
x
0
,
y
0
)
∂
y
(
y
−
y
0
)
h(x,y)\approx h(x_0,y_0)+\frac{\partial h(x_0,y_0)}{\partial x}(x-x_0)+\frac{\partial h(x_0,y_0)}{\partial y}(y-y_0)
h(x,y)≈h(x0,y0)+∂x∂h(x0,y0)(x−x0)+∂y∂h(x0,y0)(y−y0)
因此,在任意点
(
a
,
b
)
(a,b)
(a,b)处我们可以将损失函数用泰勒展示展开,并且当红色圆圈足够小时,圆圈内的函数值可以近似为
L
(
θ
)
≈
L
(
a
,
b
)
+
∂
L
(
a
,
b
)
∂
θ
1
(
θ
1
−
a
)
+
∂
L
(
a
,
b
)
∂
θ
2
(
θ
2
−
b
)
L(\theta)\approx L(a,b)+\frac{\partial L(a,b)}{\partial\theta_1}(\theta_1-a)+\frac{\partial L(a,b)}{\partial\theta_2}(\theta_2-b)
L(θ)≈L(a,b)+∂θ1∂L(a,b)(θ1−a)+∂θ2∂L(a,b)(θ2−b)
其中,
L
(
a
,
b
)
L(a,b)
L(a,b),
∂
L
(
a
,
b
)
∂
θ
1
\frac{\partial L(a,b)}{\partial\theta_1}
∂θ1∂L(a,b)和
∂
L
(
a
,
b
)
∂
θ
2
\frac{\partial L(a,b)}{\partial\theta_2}
∂θ2∂L(a,b)都是常数,分别令其等于
s
s
s、
u
u
u和
v
v
v,所以
L
(
θ
)
≈
s
+
u
(
θ
1
−
a
)
+
v
(
θ
2
−
b
)
L(\theta)\approx s+u(\theta_1-a)+v(\theta_2-b)
L(θ)≈s+u(θ1−a)+v(θ2−b)
我们需要在圆圈内找出一组
θ
1
\theta_1
θ1,
θ
2
\theta_2
θ2使得
L
(
θ
)
L(\theta)
L(θ)最小,形式化表达如下:
min
θ
L
(
θ
)
≈
s
+
u
(
θ
1
−
a
)
+
v
(
θ
2
−
b
)
s
.
t
.
(
θ
1
−
a
)
2
+
(
θ
2
−
b
)
2
≤
d
2
\min_\theta\quad L(\theta)\approx s+u(\theta_1-a)+v(\theta_2-b)\\ s.t.\quad(\theta_1-a)^2+(\theta_2-b)^2\le d^2
θminL(θ)≈s+u(θ1−a)+v(θ2−b)s.t.(θ1−a)2+(θ2−b)2≤d2
优化目标和约束中都有
(
θ
1
−
a
)
(\theta_1-a)
(θ1−a)和
(
θ
2
−
b
)
(\theta_2-b)
(θ2−b),分别用
Δ
θ
1
\Delta\theta_1
Δθ1和
Δ
θ
2
\Delta\theta_2
Δθ2代替
min
θ
L
(
θ
)
≈
s
+
u
Δ
θ
1
+
v
Δ
θ
2
s
.
t
.
Δ
θ
1
2
+
Δ
θ
2
2
≤
d
2
\min_\theta\quad L(\theta)\approx s+u\Delta\theta_1+v\Delta\theta_2\\ s.t.\quad{\Delta\theta_1}^2+{\Delta\theta_2}^2\le d^2
θminL(θ)≈s+uΔθ1+vΔθ2s.t.Δθ12+Δθ22≤d2
观察
u
Δ
θ
1
+
v
Δ
θ
2
u\Delta\theta_1+v\Delta\theta_2
uΔθ1+vΔθ2的形式,可以看作是两个向量
(
u
,
v
)
(u,v)
(u,v),
(
θ
1
,
θ
2
)
(\theta_1,\theta_2)
(θ1,θ2)的内积,要使向量内积最小,只需
(
θ
1
,
θ
2
)
(\theta_1,\theta_2)
(θ1,θ2)的方向正好与
(
u
,
v
)
(u,v)
(u,v)的方向相反,同时
(
θ
1
,
θ
2
)
(\theta_1,\theta_2)
(θ1,θ2)的长度达到圆的半径,所以
[
Δ
θ
1
Δ
θ
2
]
=
−
η
[
u
v
]
⟹
[
θ
1
θ
2
]
=
[
a
b
]
−
η
[
∂
L
(
a
,
b
)
∂
θ
1
∂
L
(
a
,
b
)
∂
θ
2
]
\begin{aligned} \begin{bmatrix} \Delta\theta_1 \\ \Delta\theta_2 \end{bmatrix}=-\eta \begin{bmatrix} u \\ v \end{bmatrix} \Longrightarrow \begin{bmatrix} \theta_1 \\ \theta_2 \end{bmatrix}= \begin{bmatrix} a \\ b \end{bmatrix}-\eta \begin{bmatrix} \frac{\partial L(a,b)}{\partial\theta_1} \\ \frac{\partial L(a,b)}{\partial\theta_2} \end{bmatrix} \end{aligned}
[Δθ1Δθ2]=−η[uv]⟹[θ1θ2]=[ab]−η[∂θ1∂L(a,b)∂θ2∂L(a,b)]
经过上面的推导,我们很好的解释了为什么要沿着梯度的反方向更新参数,并且也解释了学习速率 η \eta η不能设置过大,否则 L ( θ ) ≈ s + u Δ θ 1 + v Δ θ 2 L(\theta)\approx s+u\Delta\theta_1+v\Delta\theta_2 L(θ)≈s+uΔθ1+vΔθ2将不再成立。
梯度下降的一些技巧
1、学习速率(learning rate)
学习速率是最需要调整的一个超参数,太小会使得训练速度过慢;太大会使得训练无法收敛,因此需要很小心的调节学习速率
η
\eta
η。
我们可以绘出损失函数的曲线图,如上图左边所示,红色的学习速率最合适,蓝色的太小,绿色的偏大,黄色则非常大。但是当参数数目很多时将无法可视化损失函数曲线,这时我们可以绘制出随迭代次数增加损失值变化曲线,如上图右边所示。如果损失下降很慢(蓝色),可能学习速率过低;如果损失开始下降很快,但很快稳定在一个较大的值(绿色),可能学习速率偏大了;如果损失不降返升(黄色),学习速率可能过大了;只有损失以恰当的速度降到很小(红色),才是最佳学习速率。
2、Adagrad
大家都有一个直观的想法:在初始距离最低点很远时,给予较大的学习速率,使得损失迅速下降;快要接近最低点时,给与较小的学习速率,确保能够到达最低点。也就是说,随着迭代次数的增加,学习速率逐渐减小
η
t
=
η
t
+
1
\eta^t=\frac{\eta}{\sqrt{ t+1}}
ηt=t+1η
每次迭代时,对所有参数都给予同样大小的参数,可能仍然不够精细,最好是学习速率能够因参数而异,Adagrad是最常用的方法,每个参数的学习速率都除上该参数之前所有微分的均方根。
w
t
+
1
←
w
t
−
η
t
σ
t
g
t
w^{t+1}\gets w^t-\frac{\eta^t}{\sigma^t}g^t
wt+1←wt−σtηtgt
g
t
=
∂
L
(
θ
t
)
∂
w
g^t=\dfrac{\partial L(\theta^t)}{\partial w}
gt=∂w∂L(θt)是
θ
t
\theta^t
θt处的梯度值,
σ
t
\sigma^t
σt是之前所有微分的均方根。例如:
σ
0
=
(
g
0
)
2
σ
1
=
1
2
[
(
g
0
)
2
+
(
g
1
)
2
]
σ
2
=
1
3
[
(
g
0
)
2
+
(
g
1
)
2
+
(
g
2
)
2
]
⋮
σ
t
=
1
t
+
1
∑
i
=
0
t
(
g
i
)
2
\begin{aligned} \sigma^0&=\sqrt{(g^0)^2}\\ \sigma^1&=\sqrt{\frac{1}{2}[(g^0)^2+(g^1)^2]}\\ \sigma^2&=\sqrt{\frac{1}{3}[(g^0)^2+(g^1)^2+(g^2)^2]}\\ \vdots\\ \sigma^t&=\sqrt{\frac{1}{t+1}\sum_{i=0}^t(g^i)^2}\\ \end{aligned}
σ0σ1σ2⋮σt=(g0)2=21[(g0)2+(g1)2]=31[(g0)2+(g1)2+(g2)2]=t+11i=0∑t(gi)2
同时,
η
t
=
η
t
+
1
\eta^t=\dfrac{\eta}{\sqrt{t+1}}
ηt=t+1η,上式可以化简为
w
t
+
1
←
w
t
−
η
∑
i
=
0
t
(
g
i
)
2
g
t
w^{t+1}\gets w^t-\frac{\eta}{\sqrt{\sum_{i=0}^t(g^i)^2}}g^t
wt+1←wt−∑i=0t(gi)2ηgt
下面尝试对Adagrad做一个解释,首先需要考虑的是:梯度越大,距离最低点越远,步伐越大?还是以两参数为例:
如果分别考虑每一维变量,确实是梯度越大,距离最低点越远,但是对比
a
a
a点和
c
c
c点,
c
c
c点的梯度大于
a
a
a点的梯度,但是
c
c
c点距离最低点更近,这说明梯度越大,距离最低点越远并不总是成立。所以在更新参数时,并不是梯度越大,步伐就可以调的越大。
考虑二次函数
y
=
a
x
2
+
b
x
+
c
y=ax^2+bx+c
y=ax2+bx+c,点
x
0
x_0
x0距最低点的距离是
∣
x
0
+
b
2
a
∣
|x_0+\dfrac{b}{2a}|
∣x0+2ab∣,也就是
∣
2
a
x
0
+
b
∣
2
a
\dfrac{|2ax_0+b|}{2a}
2a∣2ax0+b∣,所以最佳步伐应该是
∣
2
a
x
0
+
b
∣
2
a
\dfrac{|2ax_0+b|}{2a}
2a∣2ax0+b∣,分子是一阶微分的绝对值,与梯度对应,分母是二阶微分,这表明在选择最佳步伐时,我们还要考虑二阶微分。
The best step is 一 阶 微 分 二 阶 微 分 \frac{一阶微分}{二阶微分} 二阶微分一阶微分
但是计算二阶微分意味着增加一倍的计算量,这在参数很多时是不划算的,因此Adagrad采用所有一阶微分的均方根作为等价替代。
3、随机梯度下降(Stochastic Gradient Descent)or 小批量梯度下降(Mini-Batch Gradient Descent)
常规的梯度下降也就是批量梯度下降,是在整个数据集上求偏导,在该方法中,每次更新我们需要计算整个数据集中每个样本点的误差,因此速度会比较慢,对于很大的数据集,内存可能无法容纳以至无法使用,因此在实际中一般使用随机梯度下降(Stochastic Gradient Descent)或者小批量梯度下降(Mini-Batch Gradient Descent)。随机梯度下降(Stochastic Gradient Descent)的每次更新,是对数据集中的每个样本点计算损失函数,这样对于m个样本的数据集,批量梯度下降更新一次,SGD可以更新m次,虽然每次只考虑一个样本点,可能存在较大的波动,但最终都会收敛。小批量梯度下降(Mini-Batch Gradient Descent)是批量梯度下降和随机梯度下降的折中,每次更新,对数据集中部分数据计算损失函数。
4、特征缩放(Feature Scaling)
特征缩放是指将每个特征的取值限定在相同的范围
为什么要将每个特征的取值限定在相同范围呢?看下面的例子:
图中左边 x 1 x_1 x1的取值范围是 x 2 x_2 x2的百分之一,当 w 2 w_2 w2稍有变化, y y y值将变化很大,因此损失函数也将变化很大,也就是说损失函数在 w 2 w_2 w2方向下降很快,导致损失函数等高线呈扁平的椭圆形,这种情况下不用Adagrad将比较难处理,两个方向上需要不同的学习率。但经过特征缩放后,所有特征的取值范围都是统一的,损失函数等高线呈规整的圆形,梯度下降效率将比较高。