线性最小二乘法

UTF8gbsn

本文介绍线性最小二乘法.
线性最小二乘法比较简单并且在很多场景里面都有应用.
下面我们就来举几个例子.

例子

已知散点集合 X = { x 1 , x 2 , ⋯   , x n } , Y = { y 1 , y 2 , ⋯   , y n } X=\{x_1,x_2,\cdots, x_n\}, Y=\{y_1,y_2,\cdots, y_n\} X={x1,x2,,xn},Y={y1,y2,,yn},
求参数方程 y = a x + b y=ax+b y=ax+b.

在这里插入图片描述

已知是 X , Y X,Y X,Y未知是 a , b a,b a,b. 这个问题是一个标准的可以使用最小二乘方法的问题.
我们希望残差的平方和最小. 也就是 y = a x + b y=ax+b y=ax+b更好的贴近数据集 X , Y X,Y X,Y.

r i = y i − ( a x i + b ) r_i=y_i-(ax_i+b) ri=yi(axi+b)

我们的代价函数定义为 F ( a , b ) = ∑ i = 1 n [ y i − ( a x i + b ) ] 2 F(a,b)=\sum_{i=1}^{n}[y_i-(ax_i+b)]^2 F(a,b)=i=1n[yi(axi+b)]2

于是最小二乘问题变化为

( a ∗ , b ∗ ) = arg ⁡ min ⁡ a , b F ( a , b ) = arg ⁡ min ⁡ a , b ∑ i = 1 n [ y i − ( a x i + b ) ] 2 (a^{*},b^{*})=\arg\min_{a,b}F(a,b)=\arg\min_{a,b}\sum_{i=1}^{n}[y_i-(ax_i+b)]^2 (a,b)=arga,bminF(a,b)=arga,bmini=1n[yi(axi+b)]2

我们把上式改写成向量的形式.

v i = ( x i , 1 ) T , g = ( a , b ) T , Y = ( y 1 , y 2 , ⋯   , y n ) T , V = ( v 1 , v 2 , ⋯   , v n ) v_i=(x_i, 1)^T, g=(a,b)^T,Y=(y_1,y_2,\cdots, y_n)^T, V=(v_1,v_2,\cdots, v_n) vi=(xi,1)T,g=(a,b)T,Y=(y1,y2,,yn)T,V=(v1,v2,,vn)

那么,向量的形式来描述上线的方程为
g ∗ = arg ⁡ min ⁡ g F ( g ) = arg ⁡ min ⁡ g ( Y − V T g ) T ( Y − V T g ) g^{*}=\arg\min_{g} F(g)=\arg\min_{g} (Y-V^Tg)^T(Y-V^Tg) g=arggminF(g)=arggmin(YVTg)T(YVTg)

那么对上式求导数并等于0可得

V V T g = V T Y ⇒ g = ( V V T ) + V T Y VV^Tg=V^TY \Rightarrow g = (VV^T)^{+}V^TY VVTg=VTYg=(VVT)+VTY

其中符号 ( V V T ) + (VV^T)^{+} (VVT)+,表示 V V T VV^T VVT的伪逆.
在这里插入图片描述

python实现代码如下.

import numpy as np
from matplotlib import pyplot as plt

N = 100
a = 0
b = 10
s = (b-a)/N
noise = 2

def linear_function(x):
    return 3.1*x+2.5


def plt_scatter(points):
    x = [cell[0] for cell in points]
    y = [cell[1] for cell in points]
    plt.scatter(x,y, s=5)

def linear_least_square(X, Y):
    M=X.dot(X.T)
    invM = np.linalg.inv(M)
    FY = X.dot(Y)
    return invM.dot(FY)

points = []
for k in range(N):
    r = 1
    if np.random.randint(2) == 0:
        r = -1
    x = a + k*s + np.random.rand()*noise * r
    r = 1
    if np.random.randint(2) == 0:
        r = -1
    y = linear_function(x) + np.random.rand()*noise *r
    points.append((x,y))

plt_scatter(points)

X = [(cell[0], 1) for cell in points]
X = np.array(X)
X = X.T
Y = [cell[1] for cell in points]
Y = np.array(Y)
Y = Y.T

g=linear_least_square(X,Y)
x1, x2 = g[0], g[1]


x_arr = []
y_arr = []

for k in range(N):
    x = a + k*s
    y = x*x1+x2
    x_arr.append(x)
    y_arr.append(y)

plt.plot(x_arr,y_arr, '-r')
plt.show()
  • 1
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值