清风建模拟合

清风建模第四讲拟合

插值和拟合的区别:

插值得到的函数一定会经过所有的点,这就会导致当多项式次数过高的时候会造成龙格现象。

而拟合得到的函数虽然并不会经过所有的点,但是得到的曲线误差尽可能地小。

例如要拟合的点为:

image-20230711135150660

数据:

image-20230711135208097

用函数y = kx + b来拟合

最小二乘法

当k和b取何值时,得到的拟合曲线最接近呢?

第一种定义:
y i ∗ = k × x i + b k , b = a r g m i n ( ∑ n = 1 n ∣ y i − y i ∗ ∣ ) y^*_i = k \times x_i + b\\ k,b = argmin(\sum_{n=1}^{n}{|y_i - y^*_i|}) yi=k×xi+bk,b=argmin(n=1nyiyi)
第二种定义:
y i ∗ = k × x i + b k , b = a r g m i n ( ∑ n = 1 n ( y i − y i ∗ ) 2 ) y^*_i = k \times x_i + b\\ k,b = argmin(\sum_{n=1}^{n}{(y_i - y^*_i)^2}) yi=k×xi+bk,b=argmin(n=1n(yiyi)2)
由于第一种定义含有绝对值,不方便求导,所以一般使用第二种定义

image-20230711140017619

于是通过得到拟合曲线

image-20230711140151571

matlab代码如下:

data.mat文件存储的x和y的值

% 加载数据
load data.mat
plot(X,Y,'o')
% 加标签
xlabel('x的值')
ylabel('y的值')

% 拟合函数y=kx+b
n = size(X,1)
k = (n*sum(X.*Y)-sum(X)*sum(Y))/(n*sum(X.*X)-sum(X)*sum(X))
b = (sum(X.*X)*sum(Y)-sum(X)*sum(X.*Y))/(n*sum(X.*X)-sum(X)*sum(X))
hold on % 继续在之前的图形上来画图形
grid on % 显示网格线
% 用匿名函数绘制图像
f = @(x) k * x + b
fplot(f,[2.5,7])
legend("原始数据的值","拟合数据的值","Location","southeast")

% 判断拟合效果
y_hat = k * X + b
SSR = sum((y_hat-mean(Y)).^2) % 回归平方和
SSE = sum((y_hat-Y).^2) % 误差平方和
SST = sum((Y-mean(Y)).^2) % 总体平方和
SST = SSE + SSR
R_2 = SSR / SST

python代码如下

data1.xlsx存储的就是开头图片中的数据

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt

# 读取数据
data = pd.read_excel('./data1.xlsx')
data = pd.DataFrame(data)
x = np.array(data.iloc[:,0])
y = np.array(data.iloc[:,1])
plt.scatter(x,y) #绘制图像

# 拟合y = kx + b
n = np.size(x)
k = (n * np.sum(x * y) - np.sum(x) * np.sum(y)) / (n * np.sum(x * x) - np.sum(x) * np.sum(x))
b = (np.sum(x * x) * np.sum(y) - np.sum(x) * np.sum(x * y)) / (n * np.sum(x * x) - np.sum(x) * np.sum(x))
y_hat = x * k + b
plt.plot(x,y_hat,'r')

# 计算R^2
SSR = np.sum((y_hat - np.mean(y)) ** 2) # 回归平方和
SSE = np.sum((y_hat - y) ** 2) # 误差平方和
SST = np.sum((y - np.mean(y)) ** 2) # 总体平方和
SST = SSE + SSR
R_2 = SSR / SST
print(R_2)
plt.show()

SST = np.sum((y - np.mean(y)) ** 2) # 总体平方和
SST = SSE + SSR
R_2 = SSR / SST
print(R_2)
plt.show()
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

天热写代码不吹空调

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值