在实际中,常常要处理由实验或测量所得到的一些离散数据。插值与拟合方法就是要通过这些数据去确定某一类已知函数的参数或寻求某个近似函数,使所得到的近似函数与已知数据有较高的拟合精度。
如果要求这个近似函数(曲线或曲面)经过所已知的所有数据点,则称此类问题为插值问题。 (不需要函数表达式)
如果不要求近似函数通过所有数据点,而是要求它能较好地反映数据变化规律的近似函数的方法称为数据拟合。(必须有函数表达式)
近似函数不一定(曲线或曲面)通过所有的数据点。
都是根据实际中一组已知数据来构造一个能够反映数据变化规律的近似函数的方法。
插值问题不一定得到近似函数的表达形式,仅通过插值方法找到未知点对应的值。数据拟合要求得到一个具体的近似函数的表达式。
当数据量不够,需要补充,且认定已有数据可信时,通常利用函数插值方法。
实际问题当中碰到的函数 f (x) 是各种各样的,有的表达式很复杂,有的甚至给不出数学的式子,只提供了一些离散数据,譬如,某些点上的函数值和导数值。
选用不同类型的插值函数,逼近的效果就不同,一般有:
Matlab 实现:实现分段线性插值不需要编制函数程序,它自身提供了内部的功能函数
interp1(一维插值)
interp2(二维)
interp3(三维)
interpn(n维)
用MATLAB作插值计算
例:从1点12点的11小时内,每隔1小时测量一次温度,测得的温度的数值依次为:5,8,9,15,25,29,31,30,22,25,27,24.试估计每隔1/10小时的温度值.
参考代码
hours=1:12;
temps=[5 8 9 15 25 29 31 30 22 25 27 24];
h=1:0.1:12;
t=interp1(hours,temps,h,'spline');
plot(hours,temps,'+',h,t,hours,temps,'r:') %作图 “r:”表示红色虚线,"+"插值点用加号表示
xlabel('Hour'),ylabel('Degrees Celsius') %xlable表示x轴标签
运行图像
例:测得平板表面3×5网格点处的温度分别为: 82 81 80 82 84 79 63 61 65 81 84 84 82 85 86 试作出平板表面的温度分布曲面z=f(x,y)的图形.
1.先在三维坐标画出原始数据,画出粗糙的温度分布曲线图.
参考代码
x=1:5;
y=1:3;
temps=[82 81 80 82 84;79 63 61 65 81;84 84 82 85 86];
mesh(x,y,temps)
2.以平滑数据,在 x、y方向上每隔0.2个单位的地方进行插值.
再输入以下命令:
参考代码
xi=1:0.2:5;
yi=1:0.2:3;
zi=interp2(x,y,temps,xi',yi,'cubic'); %“xi'”加了一撇表示转置
mesh(xi,yi,zi) %“mesh或者surf表示曲面的形式”
画出插值后的温度分布曲面图.
运行图像
例 在某海域测得一些点(x,y)处的水深z由下表给出,船的吃水深度为5英尺,在矩形区域(75,200)×(-50,150)里的哪些地方船要避免进入.
步骤:
1.输入插值基点数据
2.在矩形区域(75,200)×(-50,150)进行插值。
3. 作海底曲面图
4.作出水深小于5的海域范围,即z=5的等高线.
%程序一:插值并作海底曲面图
参考代码
x =[129.0 140.0 103.5 88.0 185.5 195.0 105.5 157.5 107.5 77.0 81.0 162.0 162.0 117.5 ];
y =[ 7.5 141.5 23.0 147.0 22.5 137.5 85.5 -6.5 -81 3.0 56.5 -66.5 84.0 -33.5 ];
z =[ 4 8 6 8 6 8 8 9 9 8 8 9 4 9 ];
x1=75:1:200;
y1=-50:1:150;
[x1,y1]=meshgrid(x1,y1);
z1=griddata(x,y,z,x1,y1,'v4');
meshc(x1,y1,z1)
运行图像
x1=75:1:200;
y1=-50:1:150;
[x1,y1]=meshgrid(x1,y1);
z1=griddata(x,y,z,x1,y1,'v4'); %插值
z1(z1>=5)=nan; %将水深大于5的置为nan,这样绘图就不会显示出来
meshc(x1,y1,z1)
运行图像
对于情况较复杂的实际问题(因素不易化简,作用机理不详)可直接使用数据组建模型,寻找简单的因果变量之间的数量关系, 从而对未知的情形作预报。这样组建的模型为拟合模型。拟合模型的组建主要是处理好观测数据的误差,使用数学表达式从数量上近似因果变量之间的关系。拟合模型的组建是通过对有关变量的观测数据的观察、分析和选择恰当的数学表达方式得到的。
曲 线 拟 合 问 题 的 提 法
已知一组(二维)数据,即平面上 n个点(xi,yi) i=1,…,n, 寻求一个函数(曲线)y=f(x), 使 f(x) 在某种准则下与所有数据点最为接近,即曲线拟合得最好.
曲线拟合问题最常用的解法——线性最小二乘法的基本思路
用MATLAB作线性最小二乘拟合
a=polyfit(x,y,m) %输入同长度的数组x,y,“m”为拟合次数
y=polyval(a,x)
用多项式拟合的命令
1)输入以下命令:
x=0:0.1:1;
y=[-0.447 1.978 3.28 6.16 7.08 7.34 …
7.66 9.56 9.48 9.30 11.2];
A=polyfit(x,y,2)
z=polyval(A,x);
plot(x,y,'k+',x,z,'r') %作出数据点和拟合曲线的图形
2)计算结果: A = -9.8108 20.1293 -0.0317
用MATLAB作非线性最小二乘拟合
MATLAB提供了求非线性最小二乘拟合的函数:lsqcurvefit.
这个命令要先建立M文件fun.m,在其中定义函数f(x).
lsqcurvefit
已知数据点: xdata=(xdata1,xdata2,…,xdatan),
ydata=(ydata1,ydata2,…,ydatan)
lsqcurvefit用以求含参量x(向量)的向量值函数
F(x,xdata)=(F(x,xdata1),…,F(x,xdatan))T
中的参变量x(向量),使得
输入格式为:
(1) x = lsqcurvefit (‘fun’,x0,xdata,ydata);
(2) x = lsqcurvefit(‘fun’,x0,xdata,ydata,options);
%fun是一个事先建立的定义函数F(x,xdata) 的M文件, 自变量为x和xdata
%x0迭代初值
%xdate已知数据点
%options选项见无约束优化
(3) x = lsqcurvefit(‘fun’,x0,xdata,ydata,options,’grad’);
(4) [x,options]=lsqcurvefit(‘fun’,x0,xdata,ydata,…);
(5) [x,options,funval]=lsqcurvefit(‘fun’,x0,xdata,ydata,…);
(6) [x,options,funval,Jacob]=lsqcurvefit(‘fun’,x0,xdata,
ydata,…);
最小二乘拟合:lsqcurvefit()
例 假设有一组实测数据
xi 0.1 0.2 0.3 0.4 0.5 0.6 0.7 0.8 0.9 1.0
yi 2.3201 2.647 2.9707 3.2885 3.6008 3.909 4.2147 4.5191 4.8232 5.1275
假设已知该数据可能满足的原型函数为
试求出满足下面数据的最小二乘解的a,b,c,d的值。
先建立原型函数:
function y=f1(a,x)
y=a(1)*x+a(2)*x.^2.*exp(-a(3)*x)+a(4);
在命令窗口中输入:
x=[0.1 0.2 0.3 0.4 0.5 0.6 0.7 0.8 0.9 1.0];
y=[2.3201 2.647 2.9707 3.2885 3.6008 3.909 4.2147 4.5191 4.8232 5.1275];
a=lsqcurvefit(‘f1’,[1;2;2;2],x,y)
plot(x,y,’+’,x,f1(a,x))
对于已给一批实测数据,由于实测方法、实验环境等一些外界因素的影响,不可避免地会产生随机干扰和误差。我们自然希望根据数据分布的总趋势去剔除观察数据中的偶然误差,这就是所谓的数据修匀(或称数据平滑)问题。