李航在其《统计学习方法》中提到,机器学习的核心由三大块组成,分别为模型、策略、算法,其实说白了,机器学习就是一个模型 + 一个损失函数 + 一个最优化算法。损失函数是为了让模型能够更好地拟合或分类数据,最优化算法是用来优化损失函数的,而在机器学习中,最常用的最优化算法应该算梯度下降了,这篇文章就来讲讲梯度下降,探究下它是如何优化损失函数的。
梯度下降原理
上文的感知机模型中有提到,梯度,其实就是求偏导,梯度下降就是沿着梯度的负方向移动。为了更直观地理解梯度下降,这里举一个网上的例子(实在想不出比这个更形象的解析了),比如我们现在站在山上的某个位置,如下图中的点A,目标是要最快速地下到山脚下,怎么一步一步走下去呢?我们可以选择往相对当前位置来说最陡峭的地方向下移动(也就是梯度的负方向),这样一直走到山脚。这个山脚有可能是整个大山的最低处(B点),也有可能是大山的局部低处(C或D点),这取决于我们移动的方向和幅度。这种情况下,梯度下降不一定能够找到全局最优解,有可能是一个局部最优解。

但如果是下面这个凸函数图,我们就一定可以移动到最低处,因为不管我们处于山上的哪一个位置,只要我们保持每次移动都是向下的,就一定能到达最低点。这种情况下,梯度下降法得到的解就一定是全局最优解。

梯度下降算法
梯度下降算法如下(该算法摘抄自李航《统计学习方法》):
输入:目标函数$f(x)$,梯度函数$g(x) = \nabla f(x)$,计算精度$\epsilon $
输出:$f(x)$的极小点$x^*$
(1) 取初始值$x^{(0)} \in R^n$,置$k=0$
(2) 计算$f(x^{(k)})$
(3) 计算梯度$g_k = g(x^{(k)})$,当$||g_k||<\epsilon$时,停止迭代,令$x^* = x^{(k)}$;否则,令$p_k = -g(x^{(k)})$,求$\lambda_k $使得$$f(x^{(k)}+ \lambda_k p_k) = min f(x^{(k)} + \lambda p_k) $$
(4) 置$x^{(k+1)} = x^{(k)} + \lambda_k p_k $,计算$f(x^{(k+1)})$,当$||f(x^{(k+1)}) - f(x^{(k)})|| < \epsilon$ 或 $x^{(k+1)} - x^{(k)} < \epsilon$时,停止迭代,令$x^* = x^{(k+1)}$
(5) 否则,令$k=k+1$,转$(3)$
这里的$p_k$是搜索方向,$\lambda_k$是步长。假设有一个损失函数$y = x^2 - 4*x - 5 $,目标是找到$x$的值使得$y$取最小值,使用梯度下降求解如下:
- 梯度
$$\nabla x = -(2*x - 4)$$ - 更新$x$的值
$$x \leftarrow x + \eta \nabla x $$
设$x$的初始值为10,学习速率$\eta$为0.2,则
第一次迭代:梯度$$\nabla x =-(2*10 - 4) = -16$$
$x$的值相应更新为$$ x = 10 - 0.2 * 16 = 6.8$$
对应的$y$值为$$y = 6.8*6.8 - 4*6.8 - 5 = 14.04$$
第二次迭代:梯度$$\nabla x =-(2*6.8 - 4) = -9.6$$
$x$的值相应更新为$$ x = 6.8 + 0.2 * (-9.6) = 4.88$$
对应的$y$值为$$y = 4.88*4.88 - 4*4.88 - 5 = -0.7056$$
如此循环迭代,直到达到指定迭代次数或者$y$值最优。这里一直迭代到第38次时,求得极小值$ y =-9.0$。因此,梯度下降就是一个不断沿着梯度的负方向移动直到达到局部或全局最优点的一个过程。

梯度下降的三种形式
梯度下降算法可以分为以下三种:
- 批量梯度下降法(Batch Gradient Descent)
- 随机梯度下降法(Stochastic Gradient Descent)
- 小批量梯度下降法(Mini-batch Gradient Descent)
损失函数
为了更好地阐明这三种方式的本质与区别,这里以线性回归模型为例。对于任意一个线性方程,我们可以写成以下形式:$$h_\theta (x)= \theta_0 + \theta_1 x_1 + \theta_2 x_2 + …+\theta_n x_n$$ 这里的$(\theta_0,\theta_1,…,\theta_n)$为参数,也称为权重。假设现在有一堆数据$X=(x^0,x^1,x^2,…,x^m)$以及对应的$y$值$Y=(y^0,y^1,y^2,…,y^m)$。我们的目标是要找到参数$(\theta_0,\theta_1,…,\theta_n)$使得$y$值与theta(符号theta在这里硬是显示不出来,我也是醉了)值尽可能地接近。这里用h_theta(x)与y的平方误差作为损失函数来评估h_theta(x)与y值的接近程度。

有了损失函数之后,我们就可以来聊一聊这三种梯度下降的形式了。
批量梯度下降法
批量梯度下降法每次迭代都需要用到全量的训练数据,优化过程比较耗时。
前面我们已经知道了梯度下降其实就是对参数求偏导,然后沿着梯度的负方向去更新参数。对于上面的损失函数$J(\theta)$,我们随机初始化权重$\theta$,然后重复执行以下更新:$$\theta_j:=\theta_j + (-\alpha \frac{\partial}{\partial\theta_j}J(\theta))$$
这里的$\theta_j:$是指分别对$j=0,1,2,…,n$个参数求偏导。$\alpha$指学习速率,代表每次向着$J(\theta)$最陡峭的方向移动的步幅。从上面公式可以看到,为了更新参数$\theta_j:$,式子右边的$\frac{\partial}{\partial\theta_j}J(\theta))$我们还没有知道的。当我们只有一个数据点$(x,y)$的时候,$J$的偏导数:

因此,对于单个训练样本,其更新规则为:

对于所有的训练样本,累加上述损失函数的偏导为:

于是,每个参数的更新规则就变成为:

从上面公式可以清楚看到,参数的每一次更新(迭代)都要用到全量训练数据(下图红色框位置)

这种更新方式,在迭代过程中,参数的方差是最小的,收敛的过程也是最稳定的,但是如果训练数据量$m$很大,批量梯度下降将会是一个非常耗时的过程。
随机梯度下降法
随机梯度下降法的每次更新,是随机对一个样本求梯度并更新相应的参数。
从上面批量梯度下降法的求解过程可以看到,对于一个样本的损失函数,其对应参数的更新方式为:

这种做法在面对大数据集时不会出现冗余,能够进行快速的迭代。因为每次仅迭代一个样本,随机梯度下降法求解极值的过程,并不是总是向着整体最优的方向迭代的,参数的方差变化很大,收敛很不稳定,相比批量梯度下降会更加曲折,因此准确率相对于批量梯度下降法会有所下降。
小批量梯度下降法
小批量梯度下降法每次更新参数,仅使用一小部分的训练数据进行迭代
使用批量梯度下降法准确率很高,但是效率低,随机梯度下降法效率高,但是准确率低,而小批量梯度下降法算是批量下降法和随机梯度下降法的一种折衷,其集合了前面两种下降方法的优势,具体操作过程如下:

这里的$n$一般会选一个很小的数,比如10或者100,这样的话,在迭代过程中,参数值的方差不至于太大,收敛的过程会更加稳定。
后记
在机器学习中,梯度下降法通常用于优化损失函数,优化的过程,是沿着梯度的负方向不断逼近极值。从第二点‘梯度下降算法’里的实例图可以看到,一开始算法的下降速度很快,但是在极值附近时,算法的收敛速度很慢,比如在第二点的例子,在第四次迭代时已经逼近极小值了,但是在第38次迭代才解出极小值。另外,步长$\alpha$的选取很关键,步长过程可能会达不到极值点,甚至有可能发散,步长过短会导致收敛速度很慢。
批量梯度下降法每次迭代都用到所有训练数据,准确度高同时复杂度也高;随机梯度下降法每次迭代随机选取一个数据样本进行更新,准确度不高,复杂度较低;小批量梯度下降法集合了前面两种下降方法的优势,训练复杂度较低,精确度也较高。