来源:西电数模2024暑期双创课程作业
题目:设由实验测得的数据如下
-3 | -2 | -1 | 0 | 1 | 2 | 3 | |
4 | 2 | 3 | 0 | -1 | -2 | -5 |
试求一条二次曲线(权取),对它们进行最小二乘拟合。
目录
一、最小二乘法
最小二乘法的基本思想
在科学实验和统计分析中,常常需要从一组测试数据中确定变量 x 与 y 之间的近似函数关系,即根据给定的n个点
确定一条曲线,使得
总体上尽可能小,这种构造近似函数的方法称为曲线拟合,
称为拟合函数。
这种方法相比插值法的好处主要有三点:
①若用插值法,通过这几个已知点所求得的插值多项式必定是高次插值多项式,而高次插值是数值不稳定的。
②由于数据本身存在的误差,利用插值所得到的插值多项式必保留了所有测量误差,所得结果与实际问题误差较大。
③对数据拟合问题,一般地讲,并不要求所得到的近似解析表达式通过所有已知点,而只要求尽可能通过它们附近,这样可抵消原数据组中测量误差。
那么让最小可以吗——偏差有正有负,在求和时可能互相抵消。
那么让——可以,但有绝对值符号,不便于分析。
最终,我们选择最小作为我们的标准。
拟合函数![S\left ( x \right )](https://latex.csdn.net/eq?S%5Cleft%20%28%20x%20%5Cright%20%29)
一般而言,是由m个线性无关函数,
,...,
(基函数)线性组合而成,即
常用的基函数有,
,
二、用最小二乘法求解矛盾方程组
矛盾方程组
求解线性方程组时,通常要求未知数的个数与方程式个数相等。若方程式的个数多于未知数的个数,方程无解,称为矛盾(超定)方程组。即:
求解过程
最小二乘法的基本思想:矛盾方程组无精确解,只能寻求某种意义下的近似解,这种近似解并非对精确解之近似,而是寻求各未知数的一组值,使方程组中各式能近似相等。令
按最小二乘法原则,求各个方程式误差平方和
若取值,使误差平方和Q达到最小,则称这组值是矛盾方程组的最优近似解。而Q可以看做m个
自变量的二次函数,且连续。故存在一组数
,使得Q达到最小(极值问题),即
可以求解出极值条件为:
这是m个未知量,m个方程组的线性方程组——对应于原矛盾方程组的正规方程组。显然,这个方程组的解也是原矛盾方程组的最优近似解。
记
则正规方程组为
解之,得到最优近似解。
三、用多项式作最小二乘曲线拟合
取基函数为,则拟合多项式为
对照上面的内容我们可以得到矛盾方程,其中
,
,
对应的正规方程组为:,方程的解
即为多项式系数。
正规方程的建立
观察到
其是对称正定的,因此,求解正规方程只需要计算和
因此总的步骤为:
1.计算正规方程组的系数矩阵和常数项各元素
2. 利用迭代法或高斯列主元法求正规方程组的解
四、MATLAB求解
1.数据录入
clear,clc
x = [-3, -2, -1, 0, 1, 2, 3]';
y = [4, 2, 3, 0, -1, -2, -5]';
m=2;%拟合的是2次多项式
2.求解系数
常规解法(不使用曲线拟合工具箱)
A=repmat(x,1,m+1).^repmat(0:m,length(x),1);%计算A
(A'*A)\(A'*y)%解使用最小二乘法得到的正规方程
a=A\y %事实上,MATLAB反斜杠运算符在欠定和超定的情况下自动会使用最小二乘法
a=flip(a')%转置并逆序,方便polyval计算
使用曲线拟合工具箱
a= polyfit(x, y, m)
3.绘图
fprintf("拟合的曲线方程为: y = %.3fx^2 + %.3fx + %.3f\n", a(1), a(2), a(3));
x_fit = linspace(min(x), max(x), 100); %生成用于绘图的 x 值
y_fit = polyval(a, x_fit); %计算拟合多项式的y 值
% 绘制原始数据点和拟合曲线
plot(x, y, 'o', x_fit, y_fit, '-');
xlabel('x');
ylabel('y');
title('拟合的曲线');
legend('数据点', '拟合曲线');
完整代码
1.使用曲线拟合工具箱
%数据录入
clear,clc
x = [-3, -2, -1, 0, 1, 2, 3]';
y = [4, 2, 3, 0, -1, -2, -5]';
m=2;%拟合的是2次多项式
%使用最小二乘法拟合
A=repmat(x,1,m+1).^repmat(0:m,length(x),1);%计算A
%(A'*A)\(A'*y)%解使用最小二乘法得到的正规方程
a=A\y;%事实上,MATLAB反斜杠运算符在欠定和超定的情况下自动会使用最小二乘法
a=flip(a');%转置并逆序,方便polyval计算
%输出结果,绘制图像
fprintf("拟合的曲线方程为: y = %.3fx^2 + %.3fx + %.3f\n", a(1), a(2), a(3));
x_fit = linspace(min(x), max(x), 100); %生成用于绘图的 x 值
y_fit = polyval(a, x_fit); %计算拟合多项式的y 值
% 绘制原始数据点和拟合曲线
plot(x, y, 'o', x_fit, y_fit, '-');
xlabel('x');
ylabel('y');
title('拟合的曲线(不使用曲线拟合工具箱)');
legend('数据点', '拟合曲线');
2.使用曲线拟合工具箱
%数据录入
clear,clc
x = [-3, -2, -1, 0, 1, 2, 3]';
y = [4, 2, 3, 0, -1, -2, -5]';
m=2;%拟合的是2次多项式
%使用 polyfit 函数进行二次曲线拟合
a= polyfit(x, y, m)
%输出结果,绘制图像
fprintf("拟合的曲线方程为: y = %.3fx^2 + %.3fx + %.3f\n", a(1), a(2), a(3));
x_fit = linspace(min(x), max(x), 100); %生成用于绘图的 x 值
y_fit = polyval(a, x_fit); %计算拟合多项式的y 值
% 绘制原始数据点和拟合曲线
plot(x, y, 'o', x_fit, y_fit, '-');
xlabel('x');
ylabel('y');
title('拟合的曲线(使用曲线拟合工具箱)');
legend('数据点', '拟合曲线');