合肥工业大学 计算机专业 计算方法实验报告
合肥工业高校 计算机与信息学院 试验报告 课 程计算方法 专业班级 学 号 姓 名 33 / 33 Java界面 其实都不难依据程序流程图就可以完成了 试验一插值与拟合 一、 试验目的 1 明确插值多项式和分段插值多项式各自的优缺点; 2 编程实现三次样条插值算法,分析试验结果体会高次插值产生的龙格现象; 3 理解最小二乘拟合,并编程实现线性拟合,驾驭非线性拟合转化为线性拟合的方法 4 运用常用的插值和拟合方法解决实际问题。 二、 试验内容 1对于fx1/1x*x实现三次样条插值 2实现最小二乘法的直线拟合 数据如下 165 123 150 123 141 187 126 172 125 148 三、 基本原理(计算公式) 1三次样条插值在每个内节点上具有2阶导数。 2 最小二乘法拟合直线为yabx,而a,b有如下等式(N为给出的数据点的总个数) ; 四、算法设计与实现(流程图,关键点) 最小二乘法直线拟合输入数据后,依据公式计算a,b。用得到的拟合直线计算预料点的近似函数值。 五、输入与输出 1三次样条插值 输入区间长度,n1个数据点,预料点 输出预料点的近似函数值,精确值,及误差 2最小二乘法直线拟合 输入n个数据点,预料点 输出预料点的近似函数值 六、结果探讨和分析 代码 三次样条插值 includeiostream includefstream define N 10 using namespace std; double u0double x{ return x-1*x-1*2*x1; } double u1double x{ return x*x*3-2*x; } double v0double x{ return x*x-1*x-1; } double v1double x{ return x*x*x-1; } double s3double x,double y,double y1,double m,double m1,double h{ return u0x*yu1x*y1h*v0x*mh*v1x*m1; } double fdouble x{ return 1/1x*x; } int main{ ifstream fin; fin.openE\\t.txt; iffin{ couterror opening streamendl; systempause; return 0; } double x[N1],y[N1],m[N1],A[N],B[N],C[N]; double h[N]; double a[N],b[N]; double f0,fn; double temp; int i; fori0;iN;i{ finx[i]y[i]; } finf0fn; h[0]x[1]-x[0]; fori1;iN;i{ h[i]x[i1]-x[i]; a[i]h[i-1]/h[i-1]h[i]; b[i]3*1-a[i]*y[i]-y[i-1]/h[i-1]a[i]*y[i1]-y[i]/h[i]; } m[1]b[1]-1-a[1]*f0; m[N-1]b[N-1]-a[N-1]*fn; fori2;iN-1;i{ m[i]b[i]; } fori1;iN;i{ B[i]2; C[i]a[i]; } fori2;iN;i{ A[i]1-a[i]; } C[1]C[1]/B[1]; m[1]m[1]/B[1]; double t; fori2;iN-2;i{ tB[i]-C[i-1]*A[i]; C[i]C[i]/t; m[i]m[i]-m[i-1]*A[i]/t; } m[N-1]m[N-1]-m[N-2]*A[N-1]/B[N-1]-C[N-2]*A[N-1]; foriN-2;i0;i--{ m[i]m[i]-C[i]*m[i1]; } coutplease输入插值节点在x[0]到x[N]范围内endl; whilecintemp{ double tttemp; iftempx[0]||tempx[N]{ cout插值节点为tt超出插值范围endl; continue; } fori1;iN;i{ iftempx[i]break; } temptemp-x[i-1]/h[i-1]; temps3temp,y[i-1],y[i],m[i-1],m[i],h[i-1]; cout插值节点为tt精确值为ftt插值结果为temp误差为ftt-tempendl; } systempause; fin.close; return 0; } 最小二乘法的直线拟合 includeiostream includefstream define n 5 using namespace std; double sumdouble x[],int k{ int i; double sum0; fori0;ik;i sumsumx[i]; return sum; } double sum2double x[],int k{ int i; double sum0; fori0;ik;i sumsumx[i]*x[i];