局部加权线性回归 实现

局部加权线性回归

依赖

import numpy as np
import matplotlib.pyplot as plt

人工数据集

n = 100
true_theta1 = np.array([1, 2]).reshape(-1,1)
true_theta2 = np.array([16, -3]).reshape(-1,1)

X = np.random.normal(3, 1, (n,1))
X = np.insert(X, 0, 1, axis = 1)

def get_y(X):
    return np.array([e @ true_theta2 if e[1]>3 else e @ true_theta1  for e in X]).reshape(-1,1)

y = get_y(X) + np.random.normal(0, 0.01, (n,1))
np.insert(X, 2, y.T, axis = 1)
plt.scatter(X[:,1], y)
<matplotlib.collections.PathCollection at 0x7efdca896fd0>

image

以上为人工数据集分布。

局部加权线性回归函数

本代码通过使用最小二乘法直接求最优解。

def lwlr(X, x, y, k):#直接返回最优解的theta
    m = X.shape[0]
    W = np.diag(np.exp(-(X[:,1]-x)**2/2/(k**2)))
    return np.linalg.pinv(X.T @ W @ X) @ X.T @ W @ y

#np.array([1,x]) @ theta ,np.array([1,x]) @ true_theta1, np.array([1,x]) @ true_theta2, get_y([[1,x]])

损失函数

损失函数如下,其中 w i = e ( x − x i ) 2 2 τ 2 w_i = e^{\frac{(x-x_i)^2}{2\tau ^2}} wi=e2τ2(xxi)2

J ( θ ) = 1 n ∑ i = 1 n w i ( X i θ − y i ) 2 = ( X θ − y ) T W ( X θ − y ) \begin{array}{rcl} J(\pmb\theta) &=& \frac{1}{n} \sum_{i=1}^{n}w_i(\pmb X_i\pmb\theta-y_i)^2 \\ &=&(\pmb X\pmb\theta-\pmb y)^T\pmb W (\pmb X\pmb\theta-\pmb y) \\ \end{array} J(θθ)==n1i=1nwi(XXiθθyi)2(XXθθyy)TWW(XXθθyy)
对表达式求导:
∂ J ( θ ) ∂ θ = ∇ θ ( ( X θ − y ) T W ( X θ − y ) ) = x = X θ − y ∂ x T W x ∂ x ∇ θ ( X θ − y ) = ( 2 W x ) T X = 2 ( X θ − y ) T W X \begin{array}{rcl} \frac{\partial J(\pmb\theta)}{\partial\pmb\theta} &=& \nabla_{\pmb \theta}((\pmb X\pmb\theta-\pmb y)^T\pmb W (\pmb X\pmb\theta-\pmb y)) \\ &\overset{\pmb{x} = \pmb X\pmb\theta-\pmb y }{=}& \frac{\partial\pmb x^T \pmb W \pmb x}{\partial \pmb x} \nabla_{\pmb \theta}(\pmb X \pmb\theta - \pmb y)\\ &=& (2\pmb W \pmb x)^T \pmb X\\ &=& 2(\pmb X\pmb\theta-\pmb y)^T \pmb W \pmb X\\ \end{array} θθJ(θθ)==xx=XXθθyy==θθ((XXθθyy)TWW(XXθθyy))xxxxTWWxxθθ(XXθθyy)(2WWxx)TXX2(XXθθyy)TWWXX

∂ J ( θ ) ∂ θ = 0 \frac{\partial J(\pmb\theta)}{\partial\pmb\theta} = \pmb 0 θθJ(θθ)=00
2 ( X θ − y ) T W X = 0 2(\pmb X\pmb\theta-\pmb y)^T \pmb W \pmb X = \pmb 0 2(XXθθyy)TWWXX=00
2 ( X θ − y ) T W X = 0 ( X θ − y ) T W X = 0 ( ( X θ ) T − y T ) W X = 0 ( θ T X T − y T ) W X = 0 θ T X T W X − y T W X = 0 θ T X T W X = y T W X X T W X θ = X T W y θ = ( X T W X ) − 1 X T W y \begin{array}{rcl} 2(\pmb X\pmb\theta - \pmb y)^T \pmb W \pmb X &=& \pmb 0\\ (\pmb X\pmb\theta - \pmb y)^T \pmb W \pmb X &=& \pmb 0\\ ((\pmb X\pmb\theta)^T - \pmb y^T)\pmb W \pmb X &=& \pmb 0\\ (\pmb\theta^T\pmb X^T - \pmb y^T)\pmb W \pmb X &=& \pmb 0\\ \pmb\theta^T\pmb X^T\pmb W \pmb X - \pmb y^T\pmb W \pmb X &=& \pmb 0\\ \pmb\theta^T\pmb X^T\pmb W \pmb X &=& \pmb y^T\pmb W \pmb X\\ \pmb X^T \pmb W\pmb X\pmb\theta &=& \pmb X^T \pmb W\pmb y \\ \pmb\theta &=& (\pmb X^T \pmb W\pmb X)^{-1}\pmb X^T \pmb W\pmb y \\ \end{array} 2(XXθθyy)TWWXX(XXθθyy)TWWXX((XXθθ)TyyT)WWXX(θθTXXTyyT)WWXXθθTXXTWWXXyyTWWXXθθTXXTWWXXXXTWWXXθθθθ========0000000000yyTWWXXXXTWWyy(XXTWWXX)1XXTWWyy

预测

k=1
xrange = [x for x in np.arange(-1,10,0.1)] 
t1 = [get_y([[1,x]])[0][0] for x in xrange]
print(t1)
#print(xrange)
#print([x for x in xrange])
t2 = [(np.array([[1,x]])@ lwlr(X, x, y, k))[0][0] for x in xrange]
print(t2)
c = ['o' for x in xrange] + ['+' for x in xrange]
for xx, yy, cc in zip([xrange[:],xrange[:]],[t1[:],t2[:]], c):
    plt.scatter(xx, yy, marker = cc)
for i in xrange:
    print(f"当x点为{i},真实值为{get_y([[1, i]])},预测值为{np.array([[1, i]])@ lwlr(X, i, y, k)}")
plt.show()

!image

(●’◡’●)

局部加权线性回归需要保存训练的数据,能拟合不能确定模糊表达式的点集,其预测值主要会被附近的点影响,但远离预测值 x x x的对预测值的影响几乎为零。通过 w w w函数实现一个类钟形曲线的权重。当超参数 τ \tau τ(代码里的k)的大小能够调节钟形曲线的瘦高还是矮胖。 τ \tau τ越小,会更符合原数据,也会容易过拟合。而 τ \tau τ越大,曲线将会受很远的值影响,也会能预测出数据较少或者的位置的值。

但我所构建的数据集,其实并不符合实际,生活中的数据不应该出现毛刺,应该更平滑点如预测曲线,所以我认为预测曲线更符合实际。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值