最小二乘法(又称最小平方法)是一种数学优化技术。它通过最小化误差的平方和寻找数据的最佳函数匹配。利用最小二乘法可以简便地求得未知的数据,并使得这些求得的数据与实际数据之间误差的平方和为最小 。在图像领域,最小二乘法常用于直线、曲线拟合、平面拟合等。
首先我们来熟悉下最小二乘问题。考虑线性方程组Ax=b,其中A为mxn矩阵且m>n。这个方程一般不存在解x。因此,我们的任务是求最小化范数||A x ˉ \bar x xˉ-b||的向量 x ˉ \bar x xˉ。当x取遍所有值时,Ax将遍历A的整个列空间。因此我们的任务是在A的列空间中寻求最接近b的那个向量。因此,A x ˉ \bar x xˉ-b必然是与A的列空间垂直的向量。因此
A T ( A x ˉ − b ) = 0 A^T(A\bar x-b)=0 AT(Axˉ−b)=0
于是我们得到一个nxm的线性方程
( A T A ) x ˉ = A T b (A^TA)\bar x=A^Tb (ATA)xˉ=ATb
可以通过 x ˉ = ( A T A ) − 1 A T b \bar x=(A^TA)^{-1}A^Tb xˉ=(ATA)−1ATb来求解
这个方程有多个叫法,有些称为正规方程,有些称为法线方程。这个解 x ˉ \bar x xˉ其实就是Ax=b的最小二乘解。
很多人可能觉得这个不够直观,那么可以从另外一个角度去解释,举个例子:
{ x 1 + x 2 = 2 x 1 − x 2 = 1 x 1 + x 2 = 3 \begin{cases}x_1+x_2=2\\x_1-x_2=1\\x_1+x_2=3\end{cases} ⎩⎪⎨⎪⎧x1+x2=2x1−x2=1x1+x2=3
根据线性代数的知识,m个方程n个未知量m>n时通常无解,但是虽然不能求出Ax=b的解,那何不退而求其次,去寻找与解近似的向量 x ˉ \bar x xˉ。
那么如何定义与解相似,一般使用欧氏距离来进行度量,即两点间的距离,这其实很好理解,越相似,欧氏距离越近,这样求出的 x ˉ \bar x xˉ被称为最小二乘解。
将我们开始举的例子写成矩阵形式:
[ 1 1 1 − 1 1 1 ] [ x 1 x 2 ] = [ 2 1 3 ] \begin{bmatrix}1&1\\1&-1\\1&1\end{bmatrix}\begin{bmatrix}x_1\\x_2\end{bmatrix}=\begin{bmatrix}2\\1\\3\end{bmatrix} ⎣⎡1111−11⎦⎤[x1x2]=⎣⎡213⎦⎤
写成等价方程为:
x 1 [ 1 1 1 ] + x 2 [ 1 − 1 1 ] = [ 2 1 3 ] x_1\begin{bmatrix}1\\1\\1\end{bmatrix}+x_2\begin{bmatrix}1\\-1\\1\end{bmatrix}=\begin{bmatrix}2\\1\\3\end{bmatrix} x1⎣⎡111⎦⎤+x2⎣⎡1−11⎦⎤=⎣⎡213⎦⎤
对于任意 mxn 方程组Ax=b都可以看做向量方程:
x 1 v 1 + x 2 v 2 + . . . + x n v n = b x_1v_1+x_2v_2+...+x_nv_n=b x1v1+x2v2+...+xnvn=b
其实也就是把b 看做A的列向量的线性组合,对应的系数即为 x i x_i xi ,对于举的例子来说,就是把b表示为另外两个三维向量的线性组合,由于三维空间中两个三维向量的组合生成一个平面,方程仅当b在这个平面上才有解,推广至m个方程n个未知量m>n 时也是相同的情况。如下图所示,向量A x ˉ \bar x xˉ-b(右下图虚线部分)与A所在平面垂直,也就是该平面的法向量。
以上就是对最小二乘的直观上的解释。当然,想把最小二乘法学透彻光看这些还是不够。因为还存在非线性,带约束和不带约束等情况。
下面来介绍下最小二乘拟合平面的原理,已知空间中的一些离散点,对其进行平面拟合。首先,平面方程的一般式如下:
a x + b y + c z + d = 0 ax+by+cz+d=0 ax+by+cz+d=0
我们假设 c ≠ 0 c\neq0 c=0的情况。那么 z = − a c x − b c y − d c z=-\frac a c x- \frac b c y- \frac d c z=−cax−cby−cd
令 a 0 = − a c a_0=-\frac ac a0=−ca, a 1 = − b c a_1=-\frac bc a1=−cb , a 2 = − d c a_2=-\frac dc a2=−cd
于是 z = a 0 x + a 1 y + a 2 z=a_0 x+a_1 y+a_2 z=a0x+a1y+a2
如果该平面内存在一系列的点集 { ( x , y , z ) ∣ ( x , y , z ) ∈ ( x i , y i , z i ) , i = 0 , 1 , 2 , . . . , n − 1 } \{(x,y,z)|(x,y,z)\in(x_i,y_i,z_i),i=0,1,2,...,n-1\} {(x,y,z)∣(x,y,z)∈(xi,yi,zi),i=0,1,2,...,n−1}
按照最小二乘原则,使得误差平方和最小。
∑ i = 0 n − 1 ( z − z i ) 2 = m i n \sum_{i=0}^{n-1}{(z-z_i)^2}=min i=0∑n−1(z−zi)2=min
也就是指 S = ∑ i = 0 n − 1 ( a 0 x + a 1 y + a 2 − z i ) 2 S=\sum_{i=0}^{n-1}{(a_0 x+a_1 y+a_2-z_i)^2} S=∑i=0n−1(a0x+a1y+a2−zi)2最小,其中 a 0 , a 1 , a 2 a_0 ,a_1,a_2 a0,a1,a2是未知数。
为了使得上式最小,要求 ∂ S ∂ a k = 0 , k = 0 , 1 , 2 \frac{\partial{S}} {\partial{a_k}}=0, k=0,1,2 ∂ak∂S=0,k=0,1,2
即 { ∑ i = 0 n − 1 2 ( a 0 x i + a 1 y i + a 2 − z i ) x i = 0 对 a 0 求 偏 导 ∑ i = 0 n − 1 2 ( a 0 x i + a 1 y i + a 2 − z i ) y i = 0 对 a 1 求 偏 导 ∑ i = 0 n − 1 2 ( a 0 x i + a 1 y i + a 2 − z i ) = 0 对 a 2 求 偏 导 \begin{cases}\sum_{i=0}^{n-1}{2(a_0 x_i+a_1 y_i+a_2-z_i)x_i}=0\quad对a_0求偏导\\\sum_{i=0}^{n-1}{2(a_0 x_i+a_1 y_i+a_2-z_i)y_i}=0\quad对a_1求偏导\\\sum_{i=0}^{n-1}{2(a_0 x_i+a_1 y_i+a_2-z_i)}=0\quad\quad对a_2求偏导\end{cases} ⎩⎪⎨⎪⎧∑i=0n−12(a0xi+a1yi+a2−zi)xi=0对a0求偏导∑i=0n−12(a0xi+a1yi+a2−zi)yi=0对a1求偏导∑i=0n−12(a0xi+a1yi+a2−zi)=0对a2求偏导
化简得 { a 0 ∑ i = 0 n − 1 x i 2 + a 1 ∑ i = 0 n − 1 x i y i + a 2 ∑ i = 0 n − 1 x i = ∑ i = 0 n − 1 x i z i a 0 ∑ i = 0 n − 1 x i y i + a 1 ∑ i = 0 n − 1 y i 2 + a 2 ∑ i = 0 n − 1 y i = ∑ i = 0 n − 1 y i z i a 0 ∑ i = 0 n − 1 x i + a 1 ∑ i = 0 n − 1 y i + n a 2 = ∑ i = 0 n − 1 z i \begin{cases}a_0\sum_{i=0}^{n-1}{x_i^2}+a_1\sum_{i=0}^{n-1}{x_i y_i}+a_2\sum_{i=0}^{n-1}{x_i}=\sum_{i=0}^{n-1}{x_i z_i}\\a_0\sum_{i=0}^{n-1}{x_i y_i}+a_1\sum_{i=0}^{n-1}{y_i^2}+a_2\sum_{i=0}^{n-1}{y_i}=\sum_{i=0}^{n-1}{y_i z_i}\\a_0\sum_{i=0}^{n-1}{x_i}+a_1\sum_{i=0}^{n-1}{y_i}+na_2=\sum_{i=0}^{n-1}{z_i}\end{cases} ⎩⎪⎨⎪⎧a0∑i=0n−1xi2+a1∑i=0n−1xiyi+a2∑i=0n−1xi=∑i=0n−1xizia0∑i=0n−1xiyi+a1∑i=0n−1yi2+a2∑i=0n−1yi=∑i=0n−1yizia0∑i=0n−1xi+a1∑i=0n−1yi+na2=∑i=0n−1zi
可以将上面的式子写成矩阵形式,方便计算
[ ∑ i = 0 n − 1 x i 2 ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 y i 2 ∑ i = 0 n − 1 y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 y i n ] [ a 0 a 1 a 2 ] = [ ∑ i = 0 n − 1 x i z i ∑ i = 0 n − 1 y i z i ∑ i = 0 n − 1 z i ] \begin{bmatrix}\sum_{i=0}^{n-1}{x_i^2}&\sum_{i=0}^{n-1}{x_i y_i}&\sum_{i=0}^{n-1}{x_i}\\ \sum_{i=0}^{n-1}{x_i y_i}&\sum_{i=0}^{n-1}{y_i^2}&\sum_{i=0}^{n-1}{y_i}\\ \sum_{i=0}^{n-1}{x_i}&\sum_{i=0}^{n-1}{y_i}&n \end{bmatrix}\begin{bmatrix} a_0\\a_1\\a_2\end{bmatrix}=\begin{bmatrix} \sum_{i=0}^{n-1}{x_i z_i}\\\sum_{i=0}^{n-1}{y_i z_i}\\\sum_{i=0}^{n-1}{z_i}\end{bmatrix} ⎣⎡∑i=0n−1xi2∑i=0n−1xiyi∑i=0n−1xi∑i=0n−1xiyi∑i=0n−1yi2∑i=0n−1yi∑i=0n−1xi∑i=0n−1yin⎦⎤⎣⎡a0a1a2⎦⎤=⎣⎡∑i=0n−1xizi∑i=0n−1yizi∑i=0n−1zi⎦⎤
现在,我们马上可以得到我们想要的平面方程系数了,解这个方程有多种方法。大部分人对于SVD分解求解的方式比较熟悉,那下面介绍一种不怎么常用的方法,就是使用克拉默法则。那这个法则是什么意思呢?可以参考 链接.
总的来说,如果求解 A x = b Ax=b Ax=b就是用b分别去替换等式坐标矩阵 A A A的每一列,求出替换后的 A ′ A^{'} A′行列式,然后除以替换前的 A A A的行列式。分别求出 a i , i = 0 , 1 , 2 {a_i,i=0,1,2} ai,i=0,1,2.
所以,所得的方程系数为
a 0 = ∣ ∑ i = 0 n − 1 x i z i ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 y i z i ∑ i = 0 n − 1 y i 2 ∑ i = 0 n − 1 y i ∑ i = 0 n − 1 z i ∑ i = 0 n − 1 y i n ∣ ∣ ∑ i = 0 n − 1 x i 2 ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 y i 2 ∑ i = 0 n − 1 y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 y i n ∣ a 1 = ∣ ∑ i = 0 n − 1 x i 2 ∑ i = 0 n − 1 x i z i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 y i z i ∑ i = 0 n − 1 y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 z i n ∣ ∣ ∑ i = 0 n − 1 x i 2 ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 y i 2 ∑ i = 0 n − 1 y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 y i n ∣ a 2 = ∣ ∑ i = 0 n − 1 x i 2 ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 x i z i ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 y i 2 ∑ i = 0 n − 1 y i z i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 y i ∑ i = 0 n − 1 z i ∣ ∣ ∑ i = 0 n − 1 x i 2 ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 x i y i ∑ i = 0 n − 1 y i 2 ∑ i = 0 n − 1 y i ∑ i = 0 n − 1 x i ∑ i = 0 n − 1 y i n ∣ a_0=\frac {\left|\begin{array}{cccc} \sum_{i=0}^{n-1}{x_i z_i} & \sum_{i=0}^{n-1}{x_i y_i}&\sum_{i=0}^{n-1}{x_i}\\ \sum_{i=0}^{n-1}{y_i z_i} & \sum_{i=0}^{n-1}{y_i^2} & \sum_{i=0}^{n-1}{y_i}\\ \sum_{i=0}^{n-1}{z_i} & \sum_{i=0}^{n-1}{y_i} & n \end{array}\right|} {\left|\begin{array}{cccc} \sum_{i=0}^{n-1}{x_i^2}&\sum_{i=0}^{n-1}{x_i y_i}&\sum_{i=0}^{n-1}{x_i}\\\sum_{i=0}^{n-1}{x_i y_i}&\sum_{i=0}^{n-1}{y_i^2}&\sum_{i=0}^{n-1}{y_i}\\\sum_{i=0}^{n-1}{x_i}&\sum_{i=0}^{n-1}{y_i}&n \end{array}\right|} \quad a_1=\frac {\left|\begin{array}{cccc} \sum_{i=0}^{n-1}{x_i^2}& \sum_{i=0}^{n-1}{x_i z_i} & \sum_{i=0}^{n-1}{x_i}\\ \sum_{i=0}^{n-1}{x_i y_i} & \sum_{i=0}^{n-1}{y_i z_i} & \sum_{i=0}^{n-1}{y_i}\\ \sum_{i=0}^{n-1}{x_i} & \sum_{i=0}^{n-1}{z_i} & n \end{array}\right|} {\left|\begin{array}{cccc} \sum_{i=0}^{n-1}{x_i^2}&\sum_{i=0}^{n-1}{x_i y_i}&\sum_{i=0}^{n-1}{x_i}\\\sum_{i=0}^{n-1}{x_i y_i}&\sum_{i=0}^{n-1}{y_i^2}&\sum_{i=0}^{n-1}{y_i}\\\sum_{i=0}^{n-1}{x_i}&\sum_{i=0}^{n-1}{y_i}&n \end{array}\right|} \quad a_2=\frac {\left|\begin{array}{cccc} \sum_{i=0}^{n-1}{x_i^2} & \sum_{i=0}^{n-1}{x_i y_i}& \sum_{i=0}^{n-1}{x_i z_i}\\ \sum_{i=0}^{n-1}{x_i y_i} & \sum_{i=0}^{n-1}{y_i^2}& \sum_{i=0}^{n-1}{y_i z_i}\\ \sum_{i=0}^{n-1}{x_i} & \sum_{i=0}^{n-1}{y_i} & \sum_{i=0}^{n-1}{z_i} \end{array}\right|} {\left|\begin{array}{cccc} \sum_{i=0}^{n-1}{x_i^2}&\sum_{i=0}^{n-1}{x_i y_i}&\sum_{i=0}^{n-1}{x_i}\\\sum_{i=0}^{n-1}{x_i y_i}&\sum_{i=0}^{n-1}{y_i^2}&\sum_{i=0}^{n-1}{y_i}\\\sum_{i=0}^{n-1}{x_i}&\sum_{i=0}^{n-1}{y_i}&n \end{array}\right|} a0=∣∣∣∣∣∣∑i=0n−1xi2∑i=0n−1xiyi∑i=0n−1xi∑i=0n−1xiyi∑i=0n−1yi2∑i=0n−1yi∑i=0n−1xi∑i=0n−1yin∣∣∣∣∣∣∣∣∣∣∣∣∑i=0n−1xizi∑i=0n−1yizi∑i=0n−1zi∑i=0n−1xiyi∑i=0n−1yi2∑i=0n−1yi∑i=0n−1xi∑i=0n−1yin∣∣∣∣∣∣a1=∣∣∣∣∣∣∑i=0n−1xi2∑i=0n−1xiyi∑i=0n−1xi∑i=0n−1xiyi∑i=0n−1yi2∑i=0n−1yi∑i=0n−1xi∑i=0n−1yin∣∣∣∣∣∣∣∣∣∣∣∣∑i=0n−1xi2∑i=0n−1xiyi∑i=0n−1xi∑i=0n−1xizi∑i=0n−1yizi∑i=0n−1zi∑i=0n−1xi∑i=0n−1yin∣∣∣∣∣∣a2=∣∣∣∣∣∣∑i=0n−1xi2∑i=0n−1xiyi∑i=0n−1xi∑i=0n−1xiyi∑i=0n−1yi2∑i=0n−1yi∑i=0n−1xi∑i=0n−1yin∣∣∣∣∣∣∣∣∣∣∣∣∑i=0n−1xi2∑i=0n−1xiyi∑i=0n−1xi∑i=0n−1xiyi∑i=0n−1yi2∑i=0n−1yi∑i=0n−1xizi∑i=0n−1yizi∑i=0n−1zi∣∣∣∣∣∣
到此,平面方程系数就完成了,如果有错误的地方烦请指正。
参考链接.