经常在机器学习中的优化问题中看到一个算法,即梯度下降法,那到底什么是梯度下降法呢?
维基百科给出的定义是梯度下降法(Gradient descent)是一个一阶最优化算法,通常也称为最速下降法。 要使用梯度下降法找到一个函数的局部极小值,必须向函数上当前点对应梯度(或者是近似梯度)的反方向的规定步长距离点进行迭代搜索。如果相反地向梯度正方向迭代进行搜索,则会接近函数的局部极大值点;这个过程则被称为梯度上升法。
额,问题又来了,什么是梯度?为了避免各种复杂的说辞,咱们可以这样简单理解,在单变量的实值函数的情况,梯度就是导数,或者,对于一个线性函数,也就是线的斜率。
1.1 梯度下降法示例
举个形象的例子吧,比如当我们要做一个房屋价值的评估系统,那都有哪些因素决定或影响房屋的价值呢?比如说面积、房子的大小(几室几厅)、地段、朝向等等,这些影响房屋价值的变量被称为特征(feature)。在这里,为了简单,我们假定房屋只由一个变量影响,那就是房屋的面积。
假设有一个房屋销售的数据如下:
面积(m^2) 销售价钱(万元)
123 250
150 320
87 160
102 220
… …
插句题外话,顺便吐下槽,这套房屋价格数据在五年前可能还能买到帝都5环左右的房子,但现在只能买到二线城市的房屋了。
我们可以做出一个图,x轴是房屋的面积。y轴是房屋的售价,如下:
如果来了一个新的房子/面积,假设在房屋销售价格的记录中没有的,我们怎么办呢?
我们可以用一条曲线去尽量准的拟合这些数据,然后如果有新的输入面积,我们可以在将曲线上这个点对应的值返回。如果用一条直线去拟合房屋价格数据,可能如下图这个样子:
而图中绿色的点就是我们想要预测的点。
为了数学建模,首先给出一些概念和常用的符号。
然后便是一个典型的机器学习的过程,首先给出一个输入数据,我们的算法会通过一系列的过程得到一个估计的函数,这个函数有能力对没有见过的新数据给出一个新的估计,也被称为构建一个模型。
我们用X1,X2..Xn 去描述feature里面的分量,比如x1=房间的面积,x2=房间的朝向等等,我们可以做出一个估计函数:
θ在这儿称为参数,在这儿的意思是调整feature中每个分量的影响力,就是到底是房屋的面积更重要还是房屋的地段更重要。
如果我们令X0 = 1,就可以用向量的方式来表示了:
我们程序也需要一个机制去评估我们θ是否比较好,所以说需要对我们做出的h函数进行评估,一般这个进行评估的函数称为损失函数(loss function),描述h函数不好的程度,这里我们称这个函数为J函数。
换言之,我们把对x(i)的估计值与真实值y(i)差的平方和作为损失函数,前面乘上的系数1/2是为了方便求导(且在求导的时候,这个系数会消掉)。
如何调整θ以使得J(θ)取得最小值有很多方法,其中有最小二乘法(min square),是一种完全是数学描述的方法,另外一种就是梯度下降法。
1.2 梯度下降算法流程
梯度下降法的算法流程如下:
1)首先对θ赋值,这个值可以是随机的,也可以让θ是一个全零的向量。
2)改变θ的值,使得J(θ)按梯度下降的方向进行减少。
为了描述的更清楚,给出下面的图:
这是一个表示参数θ与误差函数J(θ)的关系图,红色的部分是表示J(θ)有着比较高的取值,我们需要的是,能够让J(θ)的值尽量的低,也就是达到深蓝色的部分(让误差/损失最小嘛)。θ0,θ1表示θ向量的两个维度。
在上面提到梯度下降法的第一步是给θ给一个初值,假设随机给的初值是在图上的十字点。
然后我们将θ按照梯度下降的方向进行调整,就会使得J(θ)往更低的方向进行变化,如下图所示,算法的结束将是在θ下降到无法继续下降为止。
当然,可能梯度下降的最终点并非是全局最小点,即也可能是一个局部最小点,如下图所示:
上面这张图就是描述的一个局部最小点,这是我们重新选择了一个初始点得到的,看来我们这个算法将会在很大的程度上被初始点的选择影响而陷入局部最小点。
下面我将用一个例子描述一下梯度减少的过程,对于我们的函数J(θ)求偏导J:
下面是更新的过程,也就是θi会向着梯度最小的方向进行减少。θi表示更新之前的值,-后面的部分表示按梯度方向减少的量,α表示步长,也就是每次按照梯度减少的方向变化多少。
一个很重要的地方值得注意的是,梯度是有方向的,对于一个向量θ,每一维分量θi都可以求出一个梯度的方向,我们就可以找到一个整体的方向,在变化的时候,我们就朝着下降最多的方向进行变化就可以达到一个最小点,不管它是局部的还是全局的。
用更简单的数学语言进行描述是这样的:
1.3 梯度下降法是否一定下降最快
梯度下降法并不一定是下降最快的方向,它只是目标函数在当前的点的切平面(当然高维问题不能叫平面)上下降最快的方向。在practical implementation中,牛顿方向(考虑海森矩阵)才一般被认为是下降最快的方向,可以达到superlinear的收敛速度。梯度下降类的算法的收敛速度一般是linear甚至sublinear的(在某些带复杂约束的问题)。
一般解释梯度下降,会用下山来举例。假设你现在在山顶处,必须抵达山脚下(也就是山谷最低处)的湖泊。但让人头疼的是,你的双眼被蒙上了无法辨别前进方向。换句话说,你不再能够一眼看出哪条路径是最快的下山路径,如下图:
最好的办法就是走一步算一步,先用脚向四周各个方向都迈出一步,试探一下周围的地势,用脚感觉下哪个方向是下降最大的方向。换言之,每走到一个位置的时候,求解当前位置的梯度,沿着梯度的负方向(当前最陡峭的位置向下)走一步。就这样,每要走一步都根据上一步所在的位置选择当前最陡峭最快下山的方向走下一步,一步步走下去,一直走到我们感觉已经到了山脚。
当然这样走下去,我们走到的可能并不一定是真正的山脚,而只是走到了某一个局部的山峰低处。换句话说,梯度下降不一定能够找到全局的最优解,也有可能只是一个局部最优解。当然,如果损失函数是凸函数,梯度下降法得到的解就一定是全局最优解。
总之,梯度下降法的优化思想是用当前位置负梯度方向作为搜索方向,因为该方向为当前位置的最快下降方向,所以也被称为是“最速下降法”。最速下降法越接近目标值,步长越小,前进越慢。梯度下降法的搜索迭代示意图如下图所示:
正因为梯度度下降法在接近最优解的区域收敛速度明显变慢,所以利用梯度下降法求解需要很多次的迭代。在机器学习中,基于基本的梯度下降法发展了两种梯度下降方法,分别为随机梯度下降法和批量梯度下降法。
普通的梯度下降算法在更新回归系数时要遍历整个数据集,是一种批处理方法,这样训练数据特别忙庞大时,可能出现如下问题:
2.1 随机梯度下降
为了解决上面的问题,实际中我们应用的是梯度下降的一种变体被称为随机梯度下降。
上面公式中的误差是针对于所有训练样本而得到的,而随机梯度下降的思想是根据每个单独的训练样本来更新权值,这样我们上面的梯度公式就变成了:
经过推导后,我们就可以得到最终的权值更新的公式:
有了上面权重的更新公式后,我们就可以通过输入大量的实例样本,来根据我们预期的结果不断地调整权值,从而最终得到一组权值使得我们的算法能够对一个新的样本输入得到正确的或无限接近的结果。
这里做一个对比
设代价函数为
参数更新为:
i是样本编号下标,j是样本维数下标,m为样例数目,n为特征数目。所以更新一个θj只需要一个样本就可以。
下面两幅图可以很形象的对比各种优化方法(图来源:http://sebastianruder.com/optimizing-gradient-descent/):
SGD各优化方法在损失曲面上的表现
从上图可以看出, Adagrad、Adadelta与RMSprop在损失曲面上能够立即转移到正确的移动方向上达到快速的收敛。而Momentum 与NAG会导致偏离(off-track)。同时NAG能够在偏离之后快速修正其路线,因为其根据梯度修正来提高响应性。
SGD各优化方法在损失曲面鞍点处上的表现
2.2 批量梯度下降
参数更新为:
i是样本编号下标,j是样本维数下标,m为样例数目,n为特征数目。所以更新一个θj需要遍历整个样本集
此外,如何优化随机梯度法呢?详情请点击:论文公开课第一期:详解梯度下降等各类优化算法(含视频和PPT下载)。
3.1 牛顿法
牛顿法(Newton's method)是一种在实数域和复数域上近似求解方程的方法。方法是使用函数f (x)的泰勒级数的前面几项来寻找方程f (x) = 0的根。牛顿法最大的特点就在于它的收敛速度很快。
具体步骤
首先,选择一个接近函数 f(x)零点的 x0,计算相应的 f(x0) 和切线斜率f'(x0)(这里f'表示函数 f 的导数)。
然后我们计算穿过点(x0, f(x0)) 并且斜率为f'(x0)的直线和 x 轴的交点的x坐标,也就是求如下方程的解:
我们将新求得的点的 x 坐标命名为x1,通常x1会比x0更接近方程f(x) = 0的解。因此我们现在可以利用x1开始下一轮迭代。迭代公式可化简为如下所示:
已经证明,如果f'是连续的,并且待求的零点x是孤立的,那么在零点x周围存在一个区域,只要初始值x0位于这个邻近区域内,那么牛顿法必定收敛。 并且,如果f'(x)不为0, 那么牛顿法将具有平方收敛的性能。粗略的说,这意味着每迭代一次,牛顿法结果的有效数字将增加一倍。
由于牛顿法是基于当前位置的切线来确定下一次的位置,所以牛顿法又被很形象地称为是"切线法"。牛顿法的搜索路径(二维情况)如下图所示:
关于牛顿法和梯度下降法的效率对比:
注:红色的牛顿法的迭代路径,绿色的是梯度下降法的迭代路径。
牛顿法的优缺点总结:
3.2 拟牛顿法
拟牛顿法(Quasi-Newton Methods)是求解非线性优化问题最有效的方法之一,于20世纪50年代由美国Argonne国家实验室的物理学家W.C.Davidon所提出来。Davidon设计的这种算法在当时看来是非线性优化领域最具创造性的发明之一。不久R. Fletcher和M. J. D. Powell证实了这种新的算法远比其他方法快速和可靠,使得非线性优化这门学科在一夜之间突飞猛进。
维基百科是这么解释拟牛顿法的
拟牛顿法是一种以牛顿法为基础设计的,求解非线性方程组或连续的最优化问题函数的零点或极大、极小值的算法。当牛顿法中所要求计算的Hessian矩阵难以甚至无法计算时,拟牛顿法便可派上用场。
拟牛顿法的本质思想是改善牛顿法每次需要求解复杂的Hessian矩阵的逆矩阵的缺陷,它使用正定矩阵来近似Hessian矩阵的逆,从而简化了运算的复杂度。
拟牛顿法和最速下降法一样只要求每一步迭代时知道目标函数的梯度。通过测量梯度的变化,构造一个目标函数的模型使之足以产生超线性收敛性。这类方法大大优于最速下降法,尤其对于困难的问题。另外,因为拟牛顿法不需要二阶导数的信息,所以有时比牛顿法更为有效。如今,优化软件中包含了大量的拟牛顿算法用来解决无约束,约束,和大规模的优化问题。
拟牛顿法的基本思想如下。
与牛顿法相同, 拟牛顿法是用一个二次函数以近似目标函数. 的二阶泰勒展开是
其中, 表示的梯度 ,表示Hessian矩阵的近似. 梯度可进一步近似为下列形式
令上式等于,计算出Newton步长,
然后构造的近似满足
上式称作割线方程组 .但当是定义在多维空间上的函数时, 从该式计算将成为一个不定问题 (未知数个数比方程式个数多).此时,构造,根据Newton步长更新当前解的处理需要回归到求解割线方程.几乎不同的拟牛顿法就有不同的选择割线方程的方法.而大多数的方法都假定具有对称性 (即满足). 另外, 下表所示的方法可用于求解; 在此, 于某些范数与尽量接近.即对于某些正定矩阵, 以以下方式更新:
近似Hessian矩阵一般以单位矩阵等作为初期值。最优化问题的解由根据近似所得的计算出的Newton步长更新得出。
以下为该算法的总结:
共轭梯度法是介于梯度下降法(最速下降法)与牛顿法之间的一个方法,它仅需利用一阶导数信息,但克服了梯度下降法收敛慢的缺点,又避免了牛顿法需要存储和计算Hessian矩阵并求逆的缺点,共轭梯度法不仅是解决大型线性方程组最有用的方法之一,也是解大型非线性最优化最有效的算法之一。
在各种优化算法中,共轭梯度法是非常重要的一种。其优点是所需存储量小,具有逐步收敛性,稳定性高,而且不需要任何外来参数。
下图为共轭梯度法和梯度下降法搜索最优解的路径对比示意图: