40 线性回归(中):如何使用最小二乘法进行直线拟合?
40 线性回归(中):如何使用最小二乘法进行直线拟合?
线性回归是机器学习和数据分析中的基础算法之一,而最小二乘法是求解线性回归问题的重要方法。本文将深入探讨最小二乘法的核心思想、数学推导过程以及如何通过矩阵运算求解系数矩阵。
使用观测值拟合
在详细阐述最小二乘法之前,我们先来回顾一下模型拟合的概念。在监督式学习中,拟合模型是指通过模型的假设和训练样本,推导出具体参数的过程。有了这些参数,我们就能对新的数据进行预测。而在线性回归中,我们需要找到观测数据之间的线性关系。
假设我们有两个观测数据,对应于二维空间中的两个点,这两个点可以确定唯一的一条直线,两者呈现线性关系。如下图所示:
之后,我们又加入了一个点。这个点不在原来的那条直线上。
这个时候,从线性方程的角度来看,就不存在精确解了。因为没有哪条直线能同时穿过这三个点。这张图片也体现了线性回归分析和求解线性方程组是不一样的,线性回归并不需要求精确解。
如果我们加入更多的观察点,就更是如此了。比如下图:
从上图中可以看出,这根直线不是完全精准地穿过这些点,而只是经过了其中两个,大部分点和这根直线有一定距离。这个时候,线性回归就有用武之地了。
由于我们假设ε的存在,因此在线性回归中,我们允许某条直线只穿过其中少量的点。不过,既然我们允许这种情况发生,那么就存在无穷多这样的直线。比如下图中随便画了几条,都是可以的。
当然,我们从直觉出发,一定不会选取那些远离这些点的直线,而是会选取尽可能靠近这些点的那些线。比如下图中展示的这两条。
好了,既然这样,我们就需要定义哪根线是最优的,以及在给出了最优的定义之后,如何能求解出这条最优的直线呢?最小二乘法可以回答这两个问题,下面我们具体来看。
最小二乘法
最小二乘法的主要思想就是求解未知参数,使得理论值与观测值之差(即误差,或者说残差)的平方和达到最小。我们可以使用下面这个公式来描述。
其中,$y_i$表示来自数据样本的观测值,而$\hat{y}$是假设的函数的理论值,$\varepsilon$就是我们之前提到的误差,在机器学习中也常被称为损失函数,它是观测值和真实值之差的平方和。最小二乘法里的“二乘”就是指的平方操作。有了这个公式,我们的目标就很清楚了,就是要发现使$\varepsilon$最小化时候的参数。
那么最小二乘法是如何利用最小化$\varepsilon$的这个条件来求解的呢?让我们从矩阵的角度出发来理解整个过程。
有了上面的定义之后,我们就可以写出最小二乘问题的矩阵形式。
$$\min||XB-Y||_2^2$$
其中$B$为系数矩阵,$X$为自变量矩阵,$Y$为因变量矩阵。换句话说,我们要在向量空间中,找到一个$B$,使向量$XB$与$Y$之间欧氏距离的平方数最小的$B$。
结合之前所讲的矩阵点乘知识,我们把上述式子改写为:
$$||XB-Y||_2^2=tr((XB-Y)'(XB-Y))$$
其中$(XB-Y)'$表示矩阵$(XB-Y)$的转置。而$tr()$函数表示取对角线上所有元素的和,对于某个矩阵$A$来说,$tr(A)$的值计算如下:
进一步,根据矩阵的运算法则,我们有:
$$tr((XB-Y)'(XB-Y))=tr(B'X'XB-B'X'Y-Y'XB+Y'Y)$$
因此我们可以得到:
$$||XB-Y||_2^2=tr((XB-Y)'(XB-Y))=tr(B'X'XB-B'X'Y-Y'XB+Y'Y)$$
我们知道,求最极值问题直接对应的就是导数为0,因此我们对上述的矩阵形式进行求导,得到如下的式子:
$$\frac{d||XB-Y||_2^2}{dB}=\frac{d(tr(B'X'XB-B'X'Y-Y'XB+Y'Y))}{dB}=X'XB+X'XB-X'Y-X'Y=2X'XB-2X'Y$$
如果要$||XB-Y||_2^2$最小,就要满足两个条件。
第一个条件是$\frac{d||XB-Y||_2^2}{dB}$为0,也就是$2X'XB-2X'Y=0$。
第二个条件是$\frac{d(2X'XB-2X'Y)}{dB}>0$。
由于$\frac{d(2X'XB-2X'Y)}{dB}=2X'X>0$,所以,第二个条件是满足的。只要$2X'XB=2X'Y$。
我们就能获得$\varepsilon$的最小值。从这个条件出发,我们就能求出矩阵$B$:
$$2X'XB=2X'Y$$
$$X'XB=X'Y$$
$$(X'X)^{-1}X'XB=(X'X)^{-1}X'Y$$
$$IB=(X'X)^{-1}X'Y$$
$$B=(X'X)^{-1}X'Y$$
其中$I$为单位矩阵。而$(X'X)^{-1}$表示$X'X$的逆矩阵。所以,最终系数矩阵为:
$$B=(X'X)^{-1}X'Y$$
补充证明和解释
为了保持推导的连贯性,在上述的推导过程中,我们跳过了几个步骤的证明。下面给出详细的解释,供读者更深入的学习和研究。
步骤a:
$$(XB)'=B'X'$$
证明:
对于$XB$中的每个元素$xb_{i,j}$,有:
而对于$(XB)'$中的每个元素$xb'_{i,j}$,有:
对于$B'$中的每个元素有:
$$b'{i,k}=b{k,i}$$
$X'$中的每个元素有:
$$x'{k,j}=x{j,k}$$
那么,对于$B'X'$中的每个元素$b'x'_{i,j}$,就有:
所以有$(XB)' = B'X'$。
步骤b:
$$(XB-Y)'=B'X'-Y'$$
证明:
和步骤a类似,对于$XB-Y$中的每个元素$xb-y'_{i,j}$有:
步骤c:
$$\frac{d(tr(B'X'Y))}{dB}=X'Y$$
证明:
同理,可以证明:
$$\frac{d(tr(Y'XB))}{dB}=(Y'X)'=X'Y$$
步骤d:
$$\frac{d(tr(B'X'XB))}{dB}=2X'XB$$
证明:
$$\frac{d(tr(B'X'XB))}{dB}=\frac{d(tr(B'(X'XB)))}{dB}+\frac{d(tr((B'X'X)B))}{dB}=(X'XB)+(B'X'X)'=X'XB+X'XB=2X'XB$$
步骤e:
常量对于变量求导为0,例如:
$$\frac{d(Y'Y)}{dB}=0$$
弄明白了这些细节上的证明,读者就能更好地理解最小二乘法中的推导步骤。不过,读者可能还是会奇怪,为什么最终要对矩阵求导数来求$\varepsilon$的最小值。最后,我们就聊聊如何使用求导获取极小值。
极值是一个函数的极大值或极小值。如果一个函数在一点的某个邻域内每个地方都有确定的值,而该点所对应的值是最大(小)的,那么这函数在该点的值就是一个极大(小)值。而函数的极值可以通过它的一阶和二阶导数来确定。
对于一元可微函数$f(x)$,它在某点$x_0$有极值的充分必要条件是$f(x)$在$x_0$的邻域上一阶可导,在$x_0$处二阶可导,且一阶导数$f'(x_0)=0$,二阶导数$f''(x_0)\neq0$。其中$f'$和$f''$分别表示一阶导数和二阶导数。
在一阶导数$f'(x_0)=0$的情况下,如果$f''(x_0)<0$,则$f$在$x_0$取得极大值;如果$f''(x_0)>0$,则$f$在$x_0$取得极小值。这就是为什么在求矩阵$B$的时候,我们要求$2X'XB-2X'Y$为$0$,并且$2X'XB-2X'Y$的导数要大于$0$,这样我们才能确保求得极小值。
总结
今天我们探讨了为什么简单的线性方程组无法满足线性函数拟合的需求,最主要的原因就是现实的观测数据往往不是精确的线性关系,存在一定的误差。我们所要做的就是,在允许一定范围的误差前提下,找到一种线性关系,尽量的满足观察数据,使得我们所定义的误差最小。
最小二乘法通过向量空间的欧氏距离之平方,定义了预测值和真实值之间的误差。在给定自变量和因变量的观测值之后,最小二乘法可以帮助我们推导出所有自变量的系数,并最小化误差。我们使用矩阵的形式,推导了整个过程。
不过,到目前为止,我们都只是从理论上理解最小二乘法,可能读者还没有太深的感触。下一节,我们将通过一个具体的例子来逐步进行演算,并使用Python代码对最终的结果进行验证。