分类目录:​​《机器学习中的数学》总目录​


有时我们需要计算输入和输出都为向量的函数的所有偏导数。包含所有这样的偏导数的矩阵被称为Jacobian矩阵。具体来说,如果我们有一个函数 f : R m → R n f:R^m\rightarrow R^n f:Rm→Rn, f f f的Jacobian矩阵 J ∈ R n × m J\in R^{n\times m} J∈Rn×m定义为:

J i , j = ∂ ∂ x j f ( x ) i J_{i, j}=\frac{\partial}{\partial x_j}f(x)_i Ji,j​=∂xj​∂​f(x)i​

有时,我们也对导数的导数感兴趣,即二阶导数。例如,有一个函数 f : R m → R n f:R^m\rightarrow R^n f:Rm→Rn, f f f的一阶导数(关于 x j x_j xj​)关于 x i x_i xi​的导数记为:

∂ 2 ∂ x i ∂ x j f ( x ) i \frac{\partial^2}{\partial x_i\partial x_j}f(x)_i ∂xi​∂xj​∂2​f(x)i​

在一维情况下,我们可以将 ∂ 2 ∂ x 2 f \frac{\partial^2}{\partial x^2}f ∂x2∂2​f记为 f ′ ′ ( x ) f''(x) f′′(x)。二阶导数告诉我们,一阶导数将如何随着输入的变化而改变。它表示只基于梯度信息的梯度下降步骤是否会产生如我们预期的那样大的改善,因此它是重要的。我们可以认为,​二阶导数是对曲率的衡量​。假设我们有一个二次函数,如果这样的函数具有零二阶导数,那就没有曲率,也就是一条完全平坦的线,仅用梯度就可以预测它的值。我们使用沿负梯度方向大小为 ϵ \epsilon ϵ的下降步,当该梯度是1时,代价函数将下降 ϵ \epsilon ϵ。如果二阶导数是负的,函数曲线向下凹陷(向上凸出),因此代价函数将下降得比 ϵ \epsilon ϵ多。如果二阶导数是正的,函数曲线是向上凹陷(向下凸出),因此代价函数将下降得比 ϵ \epsilon ϵ少。从下图可以看出不同形式的曲率如何影响基于梯度的预测值与真实的代价函数值的关系:

机器学习中的数学——Jacobian矩阵和Hessian矩阵_深度学习

当我们的函数具有多维输入时,二阶导数也有很多。我们可以将这些导数合并成一个矩阵,称为Hessian矩阵:

H ( f ) ( x ) i , j = ∂ 2 ∂ x i ∂ x j f ( x ) H(f)(x)_{i,j}=\frac{\partial^2}{\partial x_i\partial x_j}f(x) H(f)(x)i,j​=∂xi​∂xj​∂2​f(x)

Hessian等价于梯度的Jacobian矩阵。微分算子在任何二阶偏导连续的点处可交换,也就是它们的顺序可以互换:

∂ 2 ∂ x i ∂ x j f ( x ) = ∂ 2 ∂ x j ∂ x i f ( x ) \frac{\partial^2}{\partial x_i\partial x_j}f(x)=\frac{\partial^2}{\partial x_j\partial x_i}f(x) ∂xi​∂xj​∂2​f(x)=∂xj​∂xi​∂2​f(x)

这意味着 H i , j = H j , i H_{i, j}=H_{j, i} Hi,j​=Hj,i​,因此Hessian矩阵在这些点上是对称的。在深度学习背景下,我们遇到的大多数函数的Hessian几乎处处都是对称的。因为Hessian矩阵是实对称的,我们可以将其分解成一组实特征值和一组特征向量的正交基。在特定方向 d d d上的二阶导数可以写成 d T H d d^THd dTHd。当 d d d是 H H H的一个特征向量时,这个方向的二阶导数就是对应的特征值。对于其他的方向 d d d,方向二阶导数是所有特征值的加权平均,权重在0和1之间,且与 d d d夹角越小的特征向量的权重越大。最大特征值确定最大二阶导数,最小特征值确定最小二阶导数。我们可以通过(方向)二阶导数预期一个梯度下降步骤能表现得多好。我们在当前点 x ( 0 ) x^{(0)} x(0)处做函数 f ( x ) f(x) f(x)的近似二阶泰勒级数:

f ( x ) ≈ f ( x ( 0 ) ) + ( x − x ( 0 ) ) T g + 1 2 ( x − x ( 0 ) ) T H ( x − x ( 0 ) ) f(x)\approx f(x^{(0)})+(x-x^{(0)})^Tg+\frac{1}{2}(x-x^{(0)})^TH(x-x^{(0)}) f(x)≈f(x(0))+(x−x(0))Tg+21​(x−x(0))TH(x−x(0))

其中有3项:函数的原始值、函数斜率导致的预期改善和函数曲率导致的校正。当最后一项太大时,梯度下降实际上是可能向上移动的。当 g T H g g^THg gTHg为零或负时,近似的泰勒级数表明增加 ϵ \epsilon ϵ将永远使 f f f下降。在实践中,泰勒级数不会在 ϵ \epsilon ϵ大的时候也保持准确,因此在这种情况下我们必须采取更具启发式的选择。当 g T H g g^THg gTHg为正时,通过计算可得,使近似泰勒级数下降最多的最优步长为:

ϵ ∗ = g T g g T H g \epsilon^*=\frac{g^Tg}{g^THg} ϵ∗=gTHggTg​

最坏的情况下, g g g与 H H H最大特征值 λ max ⁡ λ_{\max} λmax对应的特征向量对齐,则最优步长是 1 λ max ⁡ \frac{1}{λ_{\max}} λmax1。当我们要最小化的函数能用二次函数很好地近似的情况下,Hessian的特征值决定了学习率的量级。二阶导数还可以用于确定一个临界点是否是局部极大点、全局极小点或鞍点。回想一下,在临界点处 f ′ ′ ( x ) = 0 f''(x)=0 f′′(x)=0。而 f ′ ′ ( x ) > 0 f''(x)>0 f′′(x)>0意味着 f ′ ( x ) f'(x) f′(x)会随着我们移向右边而增加,移向左边而减小,也就是 f ′ ( x − ϵ ) < 0 f'(x-\epsilon)<0 f′(x−ϵ)<0和 f ′ ( x − ϵ ) > 0 f'(x-\epsilon)>0 f′(x−ϵ)>0对足够小的 ϵ \epsilon ϵ成立。换句话说,当我们移向右边,斜率开始指向右边的上坡;当我们移向左边,斜率开始指向左边的上坡。因此我们得出结论,当 f ′ ( x ) = 0 f'(x)=0 f′(x)=0且 f ′ ′ ( x ) > 0 f''(x)>0 f′′(x)>0时, x x x是一个全局极小点。同理,当 f ′ ( x ) = 0 f'(x)=0 f′(x)=0且 f ′ ′ ( x ) < 0 f''(x)<0 f′′(x)<0时, x x x是一个局部极大点。这就是所谓的二阶导数测试。不幸的是,当 f ′ ′ ( x ) = 0 f''(x)=0 f′′(x)=0时,测试是不确定的。在这种情况下, x x x可以是一个鞍点或平坦区域的一部分。

在多维情况下,我们需要检测函数的所有二阶导数。利用Hessian的特征值分解,我们可以将二阶导数测试扩展到多维情况。在临界点处( ∇ x f ( x ) = 0 \nabla_xf(x)=0 ∇x​f(x)=0),我们通过检测Hessian的特征值来判断该临界点是一个局部极大点、全局极小点还是鞍点。当Hessian是正定的(所有特征值都是正的),则该临界点是全局极小点。因为方向二阶导数在任意方向都是正的,参考单变量的二阶导数测试就能得出此结论。同样的,当Hessian是负定的(所有特征值都是负的),这个点就是局部极大点。在多维情况下,实际上我们可以找到确定该点是否为鞍点的积极迹象(某些情况下)。如果Hessian的特征值中至少一个是正的且至少一个是负的,那么 x x x是 f f f某个横截面的局部极大点,却是另一个横截面的全局极小点,如下图所示。最后,多维二阶导数测试可能像单变量版本那样是不确定的。当所有非零特征值是同号的且至少有一个特征值是0时,这个检测就是不确定的。这是因为单变量的二阶导数测试在零特征值对应的横截面上是不确定的。

机器学习中的数学——Jacobian矩阵和Hessian矩阵_梯度下降_02

多维情况下,单个点处每个方向上的二阶导数是不同的。Hessian的条件数衡量这些二阶导数的变化范围。​当Hessian的条件数很差时,梯度下降法也会表现得很差​。这是因为一个方向上的导数增加得很快,而在另一个方向上增加得很慢。梯度下降不知道导数的这种变化,所以它不知道应该优先探索导数长期为负的方向。病态条件也导致很难选择合适的步长。步长必须足够小,以免冲过最小而向具有较强正曲率的方向上升。这通常意味着步长太小,以至于在其他较小曲率的方向上进展不明显,如下图所示:

机器学习中的数学——Jacobian矩阵和Hessian矩阵_特征值_03

我们可以使用Hessian矩阵的信息来指导搜索,以解决这个问题。其中最简单的方法是牛顿法(Newton’smethod)。牛顿法基于一个二阶泰勒展开来近似 x ( 0 ) x^{(0)} x(0)附近的 f ( x ) f(x) f(x):

f ( x ) ≈ f ( x ( 0 ) ) + ( x − x ( 0 ) ) T ∇ x f ( x ( 0 ) ) + 1 2 ( x − x ( 0 ) ) T H ( f ) ( x ( 0 ) ) ( x − x ( 0 ) ) f(x)\approx f(x^{(0)})+(x-x^{(0)})^T\nabla_xf(x^{(0)})+\frac{1}{2}(x-x^{(0)})^TH(f)(x^{(0)})(x-x^{(0)}) f(x)≈f(x(0))+(x−x(0))T∇x​f(x(0))+21​(x−x(0))TH(f)(x(0))(x−x(0))

通过计算,我们可以得到这个函数的临界点:

x ∗ = x ( 0 ) − H ( f ) ( x ( 0 ) ) − 1 ∇ x f ( x ( 0 ) ) x^*=x^{(0)}-H(f)(x^{(0)})^{-1}\nabla_xf(x^{(0)}) x∗=x(0)−H(f)(x(0))−1∇x​f(x(0))

如果 f f f是一个正定二次函数,牛顿法只要应用一次上式就能直接跳到函数的最小点。如果 f f f不是一个真正二次但能在局部近似为正定二次,牛顿法则需要多次迭代应用上式。迭代地更新近似函数和跳到近似函数的最小点可以比梯度下降更快地到达临界点。这在接近全局极小点时是一个特别有用的性质,但是在鞍点附近是有害的。当附近的临界点是最小点(Hessian的所有特征值都是正的)时牛顿法才适用,而梯度下降不会被吸引到鞍点(除非梯度指向鞍点)。

仅使用梯度信息的优化算法称为一阶优化算法,如梯度下降。使用Hessian矩阵的优化算法称为二阶最优化算法,如牛顿法​。大多数优化算法适用于各种各样的函数,但几乎都没有理论保证。因为在深度学习中使用的函数族是相当复杂的,所以深度学习算法往往缺乏理论保证。在许多其他领域,优化的主要方法是为有限的函数族设计优化算法。在深度学习的背景下,限制函数满足Lipschitz连续或其导数Lipschitz连续可以获得一些保证。Lipschitz连续函数的变化速度以Lipschitz常数 L L L为界:

∀ x , ∀ y : ∣ f ( x ) − f ( y ) ∣ ≤ L ∣ ∣ x − y ∣ ∣ 2 \forall x,\forall y:|f(x)-f(y)|\leq L||x-y||_2 ∀x,∀y:∣f(x)−f(y)∣≤L∣∣x−y∣∣2​

这个属性允许我们量化自己的假设——梯度下降等算法导致的输入的微小变化将使输出只产生微小变化,因此是很有用的。Lipschitz连续性也是相当弱的约束,并且深度学习中很多优化问题经过相对较小的修改后就能变得Lipschitz连续。最成功的特定优化领域或许是凸优化。凸优化通过更强的限制提供更多的保证。凸优化算法只对凸函数适用,即Hessian处处半正定的函数。因为这些函数没有鞍点而且其所有全局极小点必然是全局最小点,所以表现很好。然而,深度学习中的大多数问题都难以表示成凸优化的形式。凸优化仅用作一些深度学习算法的子程序。凸优化中的分析思路对证明深度学习算法的收敛性非常有用,然而一般来说,深度学习背景下凸优化的重要性大大减少。