拉格朗日和牛顿插值法的C 方法实现(数值分析上机实验)
拉格朗日插值及牛顿插值方法-空间统计-空间分析

拉格朗日插值及牛顿插值1.1.1 拉格朗日插值及牛顿插值在数值分析中,拉格朗日(Lagrange)插值法是以法国十八世纪数学家约瑟夫·拉格朗日命名的一种多项式插值方法。
许多实际问题中都用函数来表示某种内在联系或规律,而不少函数都只能通过实验和观测来了解。
如对实践中的某个物理量进行观测,在若干个不同的地方得到相应的观测值,拉格朗日插值法可以找到一个多项式,其恰好在各个观测的点取到观测到的值。
这样的多项式称为拉格朗日(插值)多项式。
数学上来说,拉格朗日插值法可以给出一个恰好穿过二维平面上若干个已知点的多项式函数。
设函数在区间[a,b]上n+1个互异节点01,,,n x x x 上的函数值分别为01,,,n y y y ,求n 次插值多项式(x)n P ,满足条件(x )y ,j 0,1,,n n j j P ==令00110L y (x)y (x)y (x)y (x)n n n n i i i l l l l ==+++=∑ (*) 其中01(x),(x),(x)n l l l 为以01,,,n x x x 为节点的n 次插值基函数,则L (x)n 是一次数不超过n 的多项式,且满足L (x )y ,j 0,1,,n n j j ==再由插值多项式的唯一性,得L (x)n n P ≡(*)式表示的插值多项式称为拉格朗日插值多项式。
特别地,n=1时称为线性插值,n=2时称为二次插值。
值得注意的是,插值基函数01(x),(x),(x)n l l l 仅由插值节点01,,,n x x x 确定,与被插函数f(x)无关。
因此,若以01,,,n x x x 为插值节点对函数f(x)1≡做插值多项式,则由(*)式可得基函数的一个性质 0L (x)1nii =≡∑还应注意,对于插值节点01,,,n x x x ,只要求它们互异,与大小次序无关。
从以上的描述可以看出,利用插值基函数很容易得到拉格朗日插值多项式,公式结构紧凑,在理论分析中甚为方便,但当插值节点增减时全部插值基函数均要随之变化,整个公式也将发生变化,这在实际计算中是很不方便的。
牛顿插值上机报告

x
1.1 1.3 1.6 1.9 2.2 2、给出 f(x)=lnx 的数值表 x 0.4 0.5 lnx -0.916291 -0.693147
f(x)
0.7651977 0.6200860 0.4554022 0.2818186 0.1103623 0.6 -0.510826 0.7 -0.356675 0.8 -0.223144
1
一 实验目的 1.了解并掌握 Newton 插值多项式,根据给定的数值表 ,构造 1,2,3,4 次 Newton 插值多项式, 列出算法并求解。 2.并与 Lagrange 插值多项式比较精度。 实验内容 1、给定数据表, 构造 1,2,3,4 次 Newton 插值多项式, 求 f(1.5)=? 并与 Lagrange 插值多项 式比较精度。
一阶插商 -0.7255585 -0.548946 -0.578612 -0.571521
二阶插商
三阶插商
四阶插商
0.353225 -0.0494433333 -0.5033354166 0.01181833333 0.06806851848 0.5194581228
P n x f x0 f x0 , x1 x x0 f x0 , x1 , x2 x x0 x x1
3
f x0 , x1,
, xn x x0
Hale Waihona Puke x xn1 Rn x f x P n x f x0 , x1 , x2 ,
, xn wn1 x , 其中wn+1 x x x0 x x1
end k k 1; end for k ans 1: 1:1 end resulty resulty y k inputx x k * resulty;
牛顿和拉格朗日插值算法源代码及流程图-报告

牛顿和拉格朗日插值算法源代码及流程图-报告流程图找站长要//编译平台:2000+vc6.0//实验一//作者:计算机科学与技术#include<stdio.h>#include<stdlib.h>#include<iostream.h>typedef struct data{float x;float y;}Data;//变量x和函数值y的结构Data d[20];//最多二十组数据float f(int s,int t)//牛顿插值法,用以返回插商{if(t==s+1)return (d[t].y-d[s].y)/(d[t].x-d[s].x);elsereturn (f(s+1,t)-f(s,t-1))/(d[t].x-d[s].x); }float Newton(float x,int count){int n;while(1){cout<<"请输入n值(即n次插值):";//获得插值次数cin>>n;if(n<=count-1)// 插值次数不得大于count-1次break;elsesystem("cls");}//初始化t,y,yt。
float t=1.0;float y=d[0].y;float yt=0.0;//计算y值for(int j=1;j<=n;j++){t=(x-d[j-1].x)*t;yt=f(0,j)*t;//cout<<f(0,j)<<endl;y=y+yt;}return y;}float lagrange(float x,int count){float y=0.0;for(int k=0;k<count;k++)//这儿默认为count-1次插值 {float p=1.0;//初始化pfor(int j=0;j<count;j++){//计算p的值if(k==j)continue;//判断是否为同一个数p=p*(x-d[j].x)/(d[k].x-d[j].x);}y=y+p*d[k].y;//求和}return y;//返回y的值}void main(){float x,y;int count;while(1){cout<<"请输入x[i],y[i]的组数,不得超过20组:";//要求用户输入数据组数cin>>count;if(count<=20)break;//检查输入的是否合法system("cls");}//获得各组数据for(int i=0;i<count;i++){cout<<"请输入第"<<i+1<<"组x的值:";cin>>d[i].x;cout<<"请输入第"<<i+1<<"组y的值:";cin>>d[i].y;system("cls");}cout<<"请输入x的值:";//获得变量x的值cin>>x;while(1){int choice=3;cout<<"请您选择使用哪种插值法计算:"<<endl;cout<<" (0):退出"<<endl;cout<<" (1):Lagrange"<<endl;cout<<" (2):Newton"<<endl;cout<<"输入你的选择:";cin>>choice;//取得用户的选择项if(choice==2){cout<<"你选择了牛顿插值计算方法,其结果为:";y=Newton(x,count);break;//调用相应的处理函数}if(choice==1){cout<<"你选择了拉格朗日插值计算方法,其结果为:"; y=lagrange(x,count);break;//调用相应的处理函数}if(choice==0)break;system("cls");cout<<"输入错误"<<endl;}cout<<x<<" , "<<y<<endl;//输出最终结果}。
C语言编程实现拉格朗日插值

就是表达出一个函数L n(x)的运算程序:能输入某个数值进去,结果以表格或图像的形式输出,实在两者都不行就最简单的输出就行简单例如:已知函数y=2x+1当然,我们不知道以上的函数,而且这个函数也假设不容易得出,所以我们要用一种通用的方法来构造一个函数L n(x)用来代替(当然,其中有误差,但没关系)这个方法是:L n(x)=∑y k l k(x) (求和范围是k=0到n)(x-x0)(x-x1)…(x-x k-1)(x-x k+1)…(x-x n)其中l k(x)= ——————————————————(k=0,1,2…n) (x k-x0)(x k-x1)…(x k-x k-1)(x k-x k+1)…(x k-x n)(中间下标相同的哪项没有!)就是讲,假设我想求L3(1.5)的话,即求当输入n=3,x=1.5时,我们所构造的函数值:L3(x)=∑y k l k(x)=y0l0(x)+y1l1(x)+y2l2(x)+y3l3(x)=1*[(x-x1)(x-x2)(x-x3)] / [(x0-x1)(x0-x2)(x0-x3)]+ 3*[(x-x0)(x-x2)(x-x3)] / [(x1-x0)(x1-x2)(x1-x3)]+ 5*[(x-x0)(x-x1)(x-x3)] / [(x2-x0)(x2-x1)(x2-x3)]+ 7*[(x-x0)(x-x1)(x-x2)] / [(x3-x0)(x3-x1)(x3-x2)]=1*[(1.5-1)(1.5-2)(1.5-3)] / [(0-1)(0-2)(0-3)]+ 3*[(1.5-0)( 1.5-2)( 1.5-3)] / [(1-0)(1-2)(1-3)]+ 5*[(1.5-0)( 1.5-1)( 1.5-3)] / [(2-0)(2-1)(2-3)]+ 7*[(1.5-0)( 1.5-1)( 1.5-2)] / [(3-0)(3-1)(3-2)]= - 0.375/6 + 3*1.125/2 + 5*1.125/2 - 7*0.375/6= -8*0.375/6+4*1.125=4.5-0.5=4按原给定的函数当然x=1.5时y也得4,用c语言编程实现。
数值分析(12)Lagrange插值与Newton插值

使
F(x0)=y0 , F(x1)=y1 , , F(xn)=yn ,
(a)
这类问题称为插值问题。 f(x) 称为被插值函数,F(x) 称为插值函数, x0 , x1, ... , xn 称为插值节点。 (a)式称为插值条件。
数值分析
数值分析
插值函数的类型
在函数空间 span i ( x )i=0 中取插值函数.
y
(g( xi ) f ( xi ))2 min
i =0
● ●
n
●
(xn ,yn)
y=g(x)
(x2 ,y2)
●
(x0 ,y0) o x0
(x1 ,y1) x1 x2 xn x
●
数值分析
数值分析
问题2:水深和流速的关系
在水文数据的测量中,不同水深的流速是不同的。水文 数据的测量是天天进行的,为了减少测量的工作量,希望确定 水深和流速之间的关系。为此测量了一系列不同水深和流速值, 下表给出了对某河流的测量数据
代数插值 当插值函数是代数多项式时,插值问题称为代 数插值。 设 Pn(x)=a0+a1x+…+anxn, (1) n次代数插值问题为:求次数≤n的多项式Pn(x),使 满足插值条件 Pn(xi)=yi,, i= 0,1,2,…,n, (2)
定理1 设x0 ,x1,…,xn 是n+1个互异节点,函数f(x)在这 组节点的值yk=f(xk)(k=0,1,…,n)是给定的,那么存在 唯一的次数≤n的多项式Pn (x)满足 Pn (xk)= yk, k=0,1,…,n。
数值分析
插值问题与拟合问题
如果可以将一个实际问题用函数来描述,那么 对这个函数性质以及运算规律的研究,就是对这一 实际问题的某些内在规律的理性揭示。 在工程实践和科学实验中,经常需要建立函数 关系,即y=f(x)。虽然从原则上说,它在某个区间 [a,b]上是存在的,但通常只能观测到它的部分信息, 即只能获取[a,b]上一系列离散点上的值,这些值构 成了观测数据。这就是说,我们只知道一张观测 数据表,
插值数值实验报告(3篇)

第1篇一、实验目的1. 理解并掌握插值法的基本原理和常用方法。
2. 学习使用拉格朗日插值法、牛顿插值法等数值插值方法进行函数逼近。
3. 分析不同插值方法的优缺点,并比较其精度和效率。
4. 通过实验加深对数值分析理论的理解和应用。
二、实验原理插值法是一种通过已知数据点来构造近似函数的方法。
它广泛应用于科学计算、工程设计和数据分析等领域。
常用的插值方法包括拉格朗日插值法、牛顿插值法、样条插值法等。
1. 拉格朗日插值法拉格朗日插值法是一种基于多项式的插值方法。
其基本思想是:给定一组数据点,构造一个次数不超过n的多项式,使得该多项式在这些数据点上的函数值与已知数据点的函数值相等。
2. 牛顿插值法牛顿插值法是一种基于插值多项式的差商的插值方法。
其基本思想是:给定一组数据点,构造一个次数不超过n的多项式,使得该多项式在这些数据点上的函数值与已知数据点的函数值相等,并且满足一定的差商条件。
三、实验内容1. 拉格朗日插值法(1)给定一组数据点,如:$$\begin{align}x_0 &= 0, & y_0 &= 1, \\x_1 &= 1, & y_1 &= 4, \\x_2 &= 2, & y_2 &= 9, \\x_3 &= 3, & y_3 &= 16.\end{align}$$(2)根据拉格朗日插值公式,构造插值多项式:$$P(x) = \frac{(x-x_1)(x-x_2)(x-x_3)}{(x_0-x_1)(x_0-x_2)(x_0-x_3)}y_0 + \frac{(x-x_0)(x-x_2)(x-x_3)}{(x_1-x_0)(x_1-x_2)(x_1-x_3)}y_1 + \frac{(x-x_0)(x-x_1)(x-x_3)}{(x_2-x_0)(x_2-x_1)(x_2-x_3)}y_2 + \frac{(x-x_0)(x-x_1)(x-x_2)}{(x_3-x_0)(x_3-x_1)(x_3-x_2)}y_3.$$(3)计算插值多项式在不同点的函数值,并与实际值进行比较。
计算方法上机实验报告——拉格朗日插值问题

计算方法上机实验报告——拉格朗日插值问题一、方法原理n次拉格朗日插值多项式为:Ln(x)=y0l0(x)+y1l1(x)+y2l2(x)+…+ynln(x) n=1时,称为线性插值,L1(x)=y0(x-x1)/(x0-x1)+y1(x-x0)/(x1-x0)=y0+(y1-x0)(x-x0)/(x1-x0) n=2时,称为二次插值或抛物线插值,精度相对高些L2(x)=y0(x-x1)(x-x2)/(x0-x1)/(x0-x2)+y1(x-x0)(x-x2)/(x1-x0)/(x1-x2)+y2(x-x0)(x-x1)/(x2-x0)/(x2-x1)二、主要思路使用线性方程组求系数构造插值公式相对复杂,可改用构造方法来插值。
对节点xi(i=0,1,…,n)中任一点xk(0<=k<=n)作一n次多项式lk(xk),使它在该点上取值为1,而在其余点xi(i=0,1,…,k-1,k+1,…,n)上为0,则插值多项式为Ln(x)=y0l0(x)+y1l1(x)+y2l2(x)+…+ynln(x)上式表明:n个点xi(i=0,1,…,k-1,k+1,…,n)都是lk(x)的零点。
可求得lk三.计算方法及过程:1.输入节点的个数n2.输入各个节点的横纵坐标3.输入插值点4.调用函数,返回z函数语句与形参说明程序源代码如下:形参与函数类型参数意义intn节点的个数doublex[n](double*x)存放n个节点的值doubley[n](double*y)存放n个节点相对应的函数值doublep指定插值点的值doublefun()函数返回一个双精度实型函数值,即插值点p处的近似函数值#include<iostream>#include<math.h>usingnamespacestd;#defineN100doublefun(double*x,double*y,intn,doublep);voidmain(){inti,n;cout<<"输入节点的个数n:";cin>>n;doublex[N],y[N],p;cout<<"pleaseinputxiangliangx="<<endl;for(i=0;i<n;i++)cin>>x[i];cout<<"pleaseinputxiangliangy="<<endl;for(i=0;i<n;i++)cin>>y[i];cout<<"pleaseinputLagelangrichazhiJieDianp="<<endl;cin>>p;cout<<"TheAnswer="<<fun(x,y,n,p)<<endl;system("pause");}doublefun(doublex[],doubley[],intn,doublep){doublez=0,s=1.0;intk=0,i=0;doubleL[N];while(k<n){if(k==0){for(i=1;i<n;i++)s=s*(p-x[i])/(x[0]-x[i]);L[0]=s*y[0];k=k+1;}else{s=1.0;for(i=0;i<=k-1;i++)s=s*((p-x[i])/(x[k]-x[i]));for(i=k+1;i<n;i++)s=s*((p-x[i])/(x[k]-x[i]));L[k]=s*y[k];k++;}}for(i=0;i<n;i++)z=z+L[i];returnz;}四.运行结果测试:五.实验分析n=2时,为一次插值,即线性插值n=3时,为二次插值,即抛物线插值n=1,此时只有一个节点,插值点的值就是该节点的函数值n<1时,结果都是返回0的;这里做了n=0和n=-7两种情况3<n<100时,也都有相应的答案常用的是线性插值和抛物线插值,显然,抛物线精度相对高些n次插值多项式Ln(x)通常是次数为n的多项式,特殊情况可能次数小于n.例如:通过三点的二次插值多项式L2(x),如果三点共线,则y=L2(x)就是一条直线,而不是抛物线,这时L2(x)是一次式。
拉格朗日插值法C语言编程

实验内容和原理或涉及的知识点公式:基点x i 的n 次插值基函数( i=0,1,…,n):ni x x x x x x x x x x x x x x x x x x x x x x x x x l j i jn i j j n i i i i i i i n i i i ,,1,0)())(())(()())(())(()(011101110 =--∏=----------=≠=+-+- n 次拉格朗日插值多项式:∑∏=≠=--=+++=n i n i j j ji j i n n n x x x x y x l y x l y x l y x P 001100)()()()( 流程图:验证例子已知如下的函数表,试编写程序,用拉格朗日插值多项式求0.5,0.7,0.85三点处的函数值。
实验结果:插值点的个数 m=3point X1=0.5P(0.5)=0.5210896825396829point X2=0.7P(0.7)=0.758588889799115point X3=0.85P(0.85)=0.9561194794143673实验代码#include <stdio.h>#include <conio.h>#include <malloc.h>float lagrange(float *x,float *y,float xx,int n) /*拉格朗日插值算法*/{int i,j;float *a,P=0.0; /*a作为临时变量,记录拉格朗日插值多项式*/a=(float *)malloc(n*sizeof(float));for(i=0;i<5;i++){a[i]=y[i];for(j=0;j<5;j++)if(j!=i) a[i]*=(xx-x[j])/(x[i]-x[j]);P+=a[i];}free(a);return P;}int main(){int i;int n;float x[5]={0.4,0.55,0.8,0.9,1};float y[5]={0.41075,0.57815,0.88811,1.02652,1.1752};float xx,P;int m;printf("Input m:");scanf("%d",&m);for(i=0;i<m;i++){printf("Input xx:");scanf("%f",&xx);P=lagrange(x,y,xx,5);printf("x=%f,P=%f\n",xx,P);getch();}}。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
数值分析上机实验
实验一
一.上机题目:
已知: 4 =2,9 =3,16 =4分别用二次Lagrange和Newton插值法求7 的近似值。
二.解题方法:
1.lagrange方法:
设x0=4,y0=2,x1=9,y1=3,x2=16,y2=4
代入方程:
(x1-X)(x2-X)/(x1-x0)(x2-x0)*y0+(x0-X)(x2-X)/(x0-x1)(x2-x1)*y1+(x1-X)(x0-X)/(x1-x2)(x0-x2)*y2
令X=7
代入方程得 Y=2.62857
2.Newton方法:
设x0=4,y0=2,x1=9,y1=3,x2=16,y2=4
建表
4 2
9 3 0.2
16 4 0.14286 -0.00476
f(x)=f(x0)+f[x0,x1](X-x0)+f[x0,x1,x2](X-x0)(X-x1)(X-x2)
令X=7
代入方程得Y=2.62857
三.算法公式步骤:
grange方法:
通过公式写出算法并得出最后的值Y:
for(b=0;b<m;b++)//完成公式f(Xn)外层嵌套循环f[b]=i//
{
double l=1;//保证每次跳出内层循环将L置1 不会将第一项的值带入下一项//
for(a=0;a<m;a++)//完成公式f(Xn)内层嵌套循环f[a]=j//
{
if(a!=b)//完成定义i=1,i!=j//
l=(f[a]-F)/(f[a]-f[b])*l;//完成(j-m)/(j-i)//
la=l*g[b];//完成公式的F(X0)=f(X0)*Y0并累乘输出结果// }
Y=la+Y;//累加x0y0+x1y1+...得最后结果//
}
2.Newton方法:
先建表,通过二维数组的思想建表
for(l=2;l<m+2;l++)//外层循环控制y阶数//
{
for(k=1;k<m+1;k++)//内层循环控制x个数//
{
a[k][l]=(a[k][l-1]-a[k-1][l-1])/(a[k][0]-a[k-l+1][0]);//完成f(x0,x1,...,xn)并存表//
}
}
填表。
通过公式求和
for(z=0;z<m;z++)
{
o=(F-f[z])*o;//完成(X-x0)(X-x1)...(X-xn)//
p=a[z+1][z+2]*o+p;//完成f(x0,x1,...,xn)*(X-x0)(X-x1)...(X-x2)的和//
q=a[0][1]+p;//加第一项f(x0)//
}
并计算出最后的值。
四.实验程序:
#include "iostream.h"
double lagrange(double F,int m,double f[],double g[]);//建立函数lagrange// double Nowton(double F,int m,double f[],double g[]); //建立函数Nowton//
int main()
{
int n;
cout<<"请输入样例点的个数n:"<<endl;
cin>>n;//输入要计算的样例点的个数//
int i;
double x[100],y[100];
for(i=0;i<n;i++)//循环输入样例点//
{
cout<<"请输入x"<<i+1<<"和y"<<i+1<<"(用空格分开):"<<endl;
cin>>x[i]>>y[i];//输入要计算的样例点//
}
double X=0;
cout<<"请输入要计算的X:"<<endl;
cin>>X;//输入要计算的点的X//
cout<<"**************************************************"<<endl;
cout<<"拉格朗日差值公式-->"<<endl;
cout<<"通过拉格朗日差值公式求得:当X="<<X<<"时,Y="<<lagrange(X,n,x,y)<<endl;//输出调用函数lagrange//
cout<<"**************************************************"<<endl;
cout<<"牛顿插值公式-->"<<endl;
cout<<"通过牛顿插值公式求得:当X="<<X<<"时,Y="<<Nowton(X,n,x,y)<<endl;//输出调用函数Nowton//
return 0;
}
double lagrange(double F,int m,double f[],double g[])
{
int a,b;
double Y=0,la=0;
for(b=0;b<m;b++)//完成公式f(Xn)外层嵌套循环f[b]=i//
{
double l=1;//保证每次跳出内层循环将L置1 不会将第一项的值带入下一项//
for(a=0;a<m;a++)//完成公式f(Xn)内层嵌套循环f[a]=j//
{
if(a!=b)//完成定义i=1,i!=j//
l=(f[a]-F)/(f[a]-f[b])*l;//完成(j-m)/(j-i)//
la=l*g[b];//完成公式的F(X0)=f(X0)*Y0并累乘输出结果// }
Y=la+Y;//累加x0y0+x1y1+...得最后结果//
}
return Y;
}
double Nowton(double F,int m,double f[],double g[])
{
int d,k,l,z;
double a[100][100],o=1,p=0,q=0;//用二维数组模拟插商表//
for(d=0;d<m;d++)//将输入数组x[]y[]赋值给二维数组前两列//
{
a[d][0]=f[d];
a[d][1]=g[d];
}
for(l=2;l<m+2;l++)//外层循环控制y阶数//
{
for(k=1;k<m+1;k++)//内层循环控制x个数//
{
a[k][l]=(a[k][l-1]-a[k-1][l-1])/(a[k][0]-a[k-l+1][0]);//完成f(x0,x1,...,xn)
并存表//
}
}
for(z=0;z<m;z++)
{
o=(F-f[z])*o;//完成(X-x0)(X-x1)...(X-xn)//
p=a[z+1][z+2]*o+p;//完成f(x0,x1,...,xn)*(X-x0)(X-x1)...(X-x2)的和//
q=a[0][1]+p;//加第一项f(x0)//
if(z+1<m)
{
cout<<"求得"<<z+1<<"阶插商为"<<a[z+1][z+2]<<endl;//输出n阶插商//
}
}
return q;
}
五.实验结果:
实验人:
07411041孙彭翔
西安电子科技大学长安学院
2010/9/23
毕业有一年了!好怀念一起打球、DOTA、三国杀的日子啊,同时感谢大家的支持!文档免费了~PS:亲爱的同学们,不能不去上课啊!。