搜档网
当前位置:搜档网 › 三次样条插值的C程序(很全啊)

三次样条插值的C程序(很全啊)

三次样条插值的C程序(很全啊)
三次样条插值的C程序(很全啊)

三次样条插值C/C++程序(自己整理的)

具体推导看书<<数值分析>>

code:

#include

using namespace std;

const int MAXN = 100;

int n;

double x[MAXN], y[MAXN]; //下标从0..n

double alph[MAXN], beta[MAXN], a[MAXN], b[MAXN];

double h[MAXN];

double m[MAXN]; //各点的一阶导数;

inline double sqr(double pa) {

return pa * pa;

}

double sunc(double p, int i) {

return (1 + 2 * (p - x[i]) / (x[i + 1] - x[i])) * sqr((p - x[i + 1]) / (x[i + 1] - x[i])) * y[i]

+ (1 + 2 * (p - x[i + 1]) / (x[i] - x[i + 1])) * sqr((p - x[i]) / (x[i + 1] - x[i])) * y[i + 1]

+ (p - x[i]) * sqr((p - x[i + 1]) / (x[i] - x[i + 1])) * m[i]

+ (p - x[i + 1]) * sqr((p - x[i]) / (x[i + 1] - x[i])) * m[i + 1];

}

int main() {

int i, j;

freopen("threeInsert.in", "r", stdin);

scanf("%d", &n);

for (i = 0; i <= n; i++) scanf("%lf%lf", &x[i], &y[i]);

// scanf("%lf%lf", &m[0], &m[n]);

for (i = 0; i <= n - 1; i++) h[i] = x[i + 1] - x[i];

//第一种边界条件

//alph[0] = 0; alph[n] = 1; beta[0] = 2 * m[0]; beta[n] = 2 * m[n];

//第二种边界条件

alph[0] = 1; alph[n] = 0; beta[0] = 3 * (y[1] - y[0]) / h[0]; beta[n] = 3 * (y[n] - y[n - 1] / h[n - 1]);

for (i = 1; i <= n - 1; i++) {

alph[i] = h[i - 1] / (h[i - 1] + h[i]);

beta[i] = 3 * ((1 - alph[i]) * (y[i] - y[i - 1]) / h[i - 1] + alph[i] * (y[i + 1] - y[i]) / h[i]);

}

a[0] = - alph[0] / 2; b[0] = beta[0] / 2;

for (i = 1; i <= n; i++) {

a[i] = - alph[i] / (2 + (1 - alph[i]) * a[i - 1]);

b[i] = (beta[i] - (1 - alph[i]) * b[i - 1]) / (2 + (1 - alph[i]) * a[i - 1]);

}

m[n + 1] = 0;

for (i = n; i >= 0; i--) {

m[i] = a[i] * m[i + 1] + b[i];

}

scanf("%lf", &xx);

for (i = 0; i < n; i++) {

if (xx >= x[i] && xx <= x[i + 1]) break ;

}

printf("%lf\n", sunc(xx, i));

}

#include

#include

using namespace std;

const int MAX = 50;

float x[MAX], y[MAX], h[MAX];//变量设置:x为各点横坐标;y为各点纵坐标;h为步长

float c[MAX], a[MAX], fxym[MAX];

float f(int x1, int x2, int x3)/*****************求差分函数(含三个参数)****************************/

{

float a = (y[x3] - y[x2]) / (x[x3] - x[x2]);

float b = (y[x2] - y[x1]) / (x[x2] - x[x1]);

return (a - b)/(x[x3] - x[x1]);

}

void cal_m(int n)/***********************用追赶法求解出弯矩向量M……***************************/

{

float B[MAX];

B[0] = c[0] / 2;

for(int i = 1; i < n; i++)

B[i] = c[i] / (2 - a[i]*B[i-1]);

//fxym[0] = fxym[0] / 2;

for(i = 1; i <= n; i++)

fxym[i] = (fxym[i] - a[i]*fxym[i-1]) / (2 - a[i]*B[i-1]);

for(i = n-1; i >= 0; i--)

fxym[i] = fxym[i] - B[i]*fxym[i+1];

}

void printout(int n);

int main()

{

int n,i; char ch;

do

{

cout<<"请输入已知断点个数:";

cin>>n;

for(i = 0; i <= n; i++)

{

cout<<"Please put in X"<

cin>>x[i]; //cout<

cout<<"Please put in Y"<

cin>>y[i]; //cout<

}

for(i = 0; i < n; i++) //求步长;其数组值较之x,y个数少一

h[i] = x[i+1] - x[i];

cout<<"Please 输入边界条件\n 1: 已知两端的一阶导数\n 2:两端的二阶导数已知\n 默认:自然边界条件\n";

int t;

float f0, f1;

cin>>t;

switch(t)

{

case 1:cout<<"Please put in Y0\' Y"<

cin>>f0>>f1;

c[0] = 1; a[n] = 1;

fxym[0] = 6*((y[1] - y[0]) / (x[1] - x[0]) - f0) / h[0]; fxym[n] = 6*(f1 - (y[n] - y[n-1]) / (x[n] - x[n-1])) / h[n-1]; break;

case 2:cout<<"Please put in Y0\" Y"<

cin>>f0>>f1;

c[0] = a[n] = 0;

fxym[0] = 2*f0; fxym[n] = 2*f1;

break;

default:cout<<"不可用\n";//待定

};//switch

for(i = 1; i < n; i++)

fxym[i] = 6 * f(i-1, i, i+1);//调用差分函数(only!)

for(i = 1; i < n; i++)

{

a[i] = h[i-1] / (h[i] + h[i-1]);

c[i] = 1 - a[i];

}

a[n] = h[n-1] / (h[n-1] + h[n]);

cal_m(n);//调用弯矩函数(only!)

cout<<"\n输出三次样条插值函数:\n";

printout(n);//调用求解三次样条插值函数;函数输出

cout<<"Do you to have anther try ? y/n :";

cin>>ch;

}

while(ch == 'y' || ch == 'Y');

return 0;

}

void printout(int n)/***************求三次样条插值函数(因已知断点个数而异)***********************/

{

cout<所包含;括号内为参数。

for(int i = 0; i < n; i++)//所输出函数个数由所设断点个数而定

{

cout<

float t = fxym[i]/(6*h[i]);

if(t > 0)

cout<

else

cout<<-t<<"*(x - "<

t = fxym[i+1]/(6*h[i]);

if(t > 0)

cout<<" + "<

else

cout<<" - "<<-t<<"*(x - "<

cout<<"\n\t";

t = (y[i] - fxym[i]*h[i]*h[i]/6)/h[i];

if(t > 0)

cout<<"+ "<

else

cout<<"- "<<-t<<"*("<

t = (y[i+1] - fxym[i+1]*h[i]*h[i]/6)/h[i];

if(t > 0)

cout<<" + "<

else

cout<<" - "<<-t<<"*(x - "<

cout<

}

cout<

}

/****************提供测试数据:(来自课本55页例5 《数值分析》清华大学出版社第四版)***********/

/*输入

3

27.7 4.1

28 4.3

29 4.1

30 3.0

1

3.0 -

4.0*/

/*输出

输出三次样条插值函数:

1: [27.7 , 28]

13.07*(x - 28)^3 + 0.22*(x - 27.7)^3

+ 14.84*(28 - x) + 14.31*(x - 27.7)

2: [28 , 29]

0.066*(29 - x)^3 + 0.1383*(x - 28)^3

+ 4.234*(29 - x) + 3.962*(x - 28)

3: [29 , 30]

0.1383*(30 - x)^3 - 1.519*(x - 29)^3

+ 3.962*(30 - x) + 4.519*(x - 29)

*/

///////////////////////////////////////////////////

// purpose:给定,值的三次样条插值多项式//

///////////////////////////////////////////////////

# define MAX_N 20 // 定义(x_i,y_i)的最大的维数

typedef struct tagPOINT // 点的结构

{

double x;

double y;

} POINT;

int main ( )

{

int n;

int i,k;

POINT points[MAX_N +1];

double h[MAX_N +1],b[MAX_N +1],c[MAX_N +1],d[MAX_N +1],M[MAX_N +1]; double u[MAX_N +1],v[MAX_N +1],y[MAX_N +1];

double x,p,q,S;

printf ("\nInput n value:"); // 输入插值点的数目

scanf ("%d",&n);

if (n>MAX_N)

{

printf ("The input n is larger than MAX_N, please redefine the MAX_N. \n"); return 1;

}

if (n<=0)

{

printf ("Please input a number between 1 and % d. \n",MAX_N);

return 1;

}

// 输入插值点(x_i,y_i),M0值和Mn值

printf ("Now input the (x_i,y_i),i=0,…,% d:\n",n);

for (i=0;i

{

scanf ("%lf %lf",&points[i].x,&points[i].y);

printf("%lf %lf\n",points[i].x,points[i].y);

}

printf ("Now input the M[0] value:");

scanf ("%lf",&M[0]);

printf ("\nNow input the M[n] value:");

scanf ("%lf",&M[n]);

printf ("\nNow input the x value:");

//输入计算三次样条插值函数的x值

scanf ("%lf",&x);

if (x>points[n-1]. x || x

{

printf ("Please input a number between %f and %f. \n",points[0].x,points[n].x); return 1;

}

// 计算M关系式中各参数的值

h[0]=points[1].x-points[0].x;

for (i=1;i

{

h[i]=points[i+1].x-points[i].x;

b[i]=h[i]/(h[i]+h[i-1]);

c[i]=1-b[i];

d[i]=6*((points[i+1].y-points[i].y)/h[i]

-(points[i].y-points[i-1].y)/h[i-1])/(h[i]+h[i-1]);

}

// 用追赶法计算Mi,i=1,…,n-1

d[1]-= c[1]*M[0];

d[n-1]-=b[n-1]*M[n];

b[n-1]=0;c[1]=0;v[0]=0;

for ( i=1;i

{

u[i]=2-c[i]*v[i-1];

v[i]=b[i]/u[i];

y[i]= (d[i]-c[i]*y[i-1])/u[i];

}

for (i=1;i

{

M[n-i]=y[n-i]-v[n-i]* M[n-i+1];

}

// 计算三次样条插值函数在x处的值

k=0;

while (x>= points[k].x) k++;

k=k-1;

p=points[k+1].x-x;q=x-points[k].x;

S=(p* p* p* M[k] +q* q* q* M[k+1]) / (6* h[k])

+( p* points [k].y+q* points[k+1].y) / h[k]-h[k]*(p* M[k] +q* M[k]+q* M[k+1])/6; printf ("S(%f ) = %f\n",x,S);

// 输出

getchar ( );

return 0;

}

#include"iostream.h"

#include"fstream.h"

#define N 100

float X[N],Y[N],M[N],a,b;

double f(int i,int j)

{

double sum1=0;

if(j-i==1) return (Y[j]-Y[i])/(X[j]-X[i]);

else return (f(i+1,j)-f(i,j-1))/(X[j]-X[i]);

}

void main()

{

ifstream istrm("E:\\data.txt");//这里是文件的输入,请相应改成普通键盘输入int n=3;

for(int i=0;i<=n;i++)

istrm>>X[i]>>Y[i];

istrm>>a>>b;

float h[N],u[N],q[N],d[N];

for(i=0;i

h[i]=X[i+1]-X[i];

q[0]=1;q[n]=0;

for(i=1;i

q[i]=h[i]/(h[i-1]+h[i]);

for(i=0;i<=n;i++)

u[i]=1-q[i];

d[0]=(6*(f(0,1)-a))/h[0];

d[n]=(6*(b-f(n-1,n)))/h[n-1];

for(i=1;i

d[i]=6*f(i-1,i+1);

float m[N];

for(i=0;i<=n;i++) m[i]=2;

for(i=1;i<=n;i++)

{

m[i]=m[i]-(u[i]/m[i-1])*q[i-1];

d[i]=d[i]-(u[i]/m[i-1])*d[i-1];

}

M[n]=d[n]/m[n];

cout<

for(i=n-1;i>=0;i--)

{

M[i]=(d[i]-q[i]*M[i+1])/m[i]; cout<

}

}

三次样条插值代码

2 三次样条插值程序 三次样条插值利用方案二(求解固支样条或压紧样条) 按照要求要起点和终点的一阶导数值已知, 可得关于01,,.....,n M M M 的严格对角占优势的三对角方程组 然后利用三对角法(追赶法)解此线性方程组。 (1)编写M 文件,并保存文件名scfit.m % x,y 分别为n 个节点的横坐标和纵坐标值组成的向量 % dx0和dxn 分别为S 的导数在x0和xn 处的值,即m 0和m n n=length(x)-1; h=diff(x); d=diff(y)./h; a=h(2:n-1); b=2*(h(1:n-1)+h(2:n)); c=h(2:n); u=6*diff(d); b(1)=b(1)-h(1)/2; u(1)=u(1)-3*(d(1)-dx0); b(n-1)=b(n-1)-h(n)/2; u(n-1)=u(n-1)-3*(dxn-d(n)); %追赶法部分 for k=2:n-1 temp=a(k-1)/b(k-1); b(k)=b(k)-temp*c(k-1); u(k)=u(k)-temp*u(k-1); end m(n)=u(n-1)/b(n-1); for k=n-2:-1:1 m(k+1)=(u(k)-c(k)*m(k+2))/b(k); end %求S K1,S K2,S K3,S K4 m(1)=3*(d(1)-dx0)/h(1)-m(2)/2; m(n+1)=3*(dxn-d(n))/h(n)-m(n)/2; for k=0:n-1 00 ()S x m '=()n n S x m '=0011111111212212n n n n n n M d M d M d M d μλμλ----??????????????????????=??????????????????????????

三次样条插值函数

沈阳航空航天大学 数学软件课程设计 (设计程序) 题目三次样条插值函数 班级 / 学号 学生姓名 指导教师

沈阳航空航天大学 课程设计任务书 课程名称数学软件课程设计 院(系)理学院专业信息与计算科学 班级学号姓名 课程设计题目三次样条插值函数 课程设计时间: 2010 年12月20日至2010 年12月31日 课程设计的内容及要求: 1.三次样条插值函数 给出函数在互异点处的值分别为。 (1)掌握求三次样条插值函数的基本原理; (2)编写程序求在第一边界条件下函数的三次样条插值函数; (3)在区间上取n=10,20,分别用等距节点对函数 作三次样条插值函数,利用(1)的结果画出插值函数的图形,并在该图形界面中同时画出的图形。 [要求] 1.学习态度要认真,要积极参与课程设计,锻炼独立思考能力; 2.严格遵守上机时间安排; 3.按照MATLAB编程训练的任务要求来编写程序; 4.根据任务书来完成课程设计论文; 5.报告书写格式要求按照沈阳航空航天大学“课程设计报告撰写规范”; 6.报告上交时间:课程设计结束时上交报告;

7.严谨抄袭行为。 指导教师年月日负责教师年月日学生签字年月日

沈阳航空航天大学 课程设计成绩评定单 课程名称数学软件课程设计 院(系)理学院专业信息与计算科学课程设计题目三次样条插值函数 学号姓名 指导教师评语: 课程设计成绩 指导教师签字 年月日

目录 一正文 (1) 1问题分析 (1) 1.1 题目 (1) 1.2 分析 (1) 2 研究方法原理 (1) 2.1 求三次样条插值多项式,算法组织 (1) 3 算例结果 (3) 二总结 (7) 参考文献 (8) 附录 (9) 源程序: (9) 程序1 (9) 程序2 (10) 程序3 (12) 程序 4 (12)

(精品)数值分析课程设计-三次样条插值

《数值分析课程设计-三次样条插值》 报告

掌握三次样条插值函数的构造方法,体会三次样条插值函数对被逼近函数的近似。 三次样条插值函数边界条件由实际问题对三次样条插值在端点的状态要求给出。 以第1 边界条件为例,用节点处二阶导数表示三次样条插值函数,用追赶法求解相关方程组。通过Matlab 编制三次样条函数的通用程序,可直接显示各区间段三次样条函数体表达式,计算出已给点插值并显示各区间分段曲线图。 引言 分段低次样条插值虽然计算简单、稳定性好、收敛性有保证且易在电子计算机上实现,但只能保证各小段曲线在连接处的连续性,不能保证整件曲线的光滑性。利用样条插值,既可保持分段低次插值多项式,又可提高插值函数光滑性。故给出分段三次样条插值的构造过程算法步骤,利用Matlab软件编写三次样条插值函数通用程序,并通过数值算例证明程序的正确性。 三次样条函数的定义及特征 定义:设[a,b] 上有插值节点,a=x1<x2<…xn=b,对应函数值为y1,y2,?yn。若函数S(x) 满 足S(xj) = yj ( j = 1,2, ?,n ), S(x) 在[xj,xj+1] ( j =1,2,?,n-1)上都是不高于三的多项式(为了与其对应j 从1 开始,在Matlab 中元素脚标从1 开始)。当S(x) 在 [a,b] 具有二阶连续导

数。则称S(x) 为三次样条插值函数。要求S(x) 只需在每个子区 间[xj,xj+1] 上确定 1 个三次多项式,设为: Sj(x)=ajx3+bjx2+cjx+dj, (j=1,2,?,n-1) (1) 其中aj,bj,cj,dj 待定,并要使它满足: S(xj)=yj, S(xj-0)=S(xj+0), (j=2,?,n-1) (2) S'(xj-0)=S'(xj+0), S"(xj-0)=S"(xj+0), (j=2,?,n-1) (3) 式(2)、(3)共给出n+3(n-2)=4n-6 个条件, 需要待定4(n-1) 个系数,因此要唯一确定三次插值函数,还要附加2 个边界条件。通常由实际问题对三次样条插值在端点的状态要求给 出。常用边界的条件有以下3 类。 第 1 类边界条件:给定端点处的一阶导数值,S'(x1)=y1',S'(xn) =yn'。 第 2 类边界条件:给定端点处的二阶导数值,S"(x1)=y1",S"(xn) =yn"。特殊情况y1"=yn"=0,称为自然边界条件。 第 3 类边界条件是周期性条件,如果y=f(x)是以b-a 为周期的函 数,于是S(x) 在端点处满足条件S'(x1+0)=S'(xn-0),S"(x+0) =S"(xn-0)。 下以第 1 边界条件为例,利用节点处二阶导数来表示三次样条插值

数值分析实验报告-插值、三次样条Word版

实验报告:牛顿差值多项式&三次样条 问题:在区间[-1,1]上分别取n=10、20用两组等距节点对龙格函数21()25f x x 作多项式插值及三次样条插值,对每个n 值,分别画出插值函数及()f x 的图形。 实验目的:通过编程实现牛顿插值方法和三次样条方法,加深对多项式插值的理解。应用所编程序解决实际算例。 实验要求: 1. 认真分析问题,深刻理解相关理论知识并能熟练应用; 2. 编写相关程序并进行实验; 3. 调试程序,得到最终结果; 4. 分析解释实验结果; 5. 按照要求完成实验报告。 实验原理: 详见《数值分析 第5版》第二章相关内容。 实验内容: (1)牛顿插值多项式 1.1 当n=10时: 在Matlab 下编写代码完成计算和画图。结果如下: 代码: clear all clc x1=-1:0.2:1; y1=1./(1+25.*x1.^2); n=length(x1); f=y1(:); for j=2:n for i=n:-1:j f(i)=(f(i)-f(i-1))/(x1(i)-x1(i-j+1)); end end syms F x p ; F(1)=1;p(1)=y1(1); for i=2:n F(i)=F(i-1)*(x-x1(i-1)); p(i)=f(i)*F(i); end

syms P P=sum(p); P10=vpa(expand(P),5); x0=-1:0.001:1; y0=subs(P,x,x0); y2=subs(1/(1+25*x^2),x,x0); plot(x0,y0,x0,y2) grid on xlabel('x') ylabel('y') P10即我们所求的牛顿插值多项式,其结果为:P10(x)=-220.94*x^10+494.91*x^8-9.5065e-14*x^7-381.43*x^6-8.504e-14*x^5+123.36*x^4+2.0 202e-14*x^3-16.855*x^2-6.6594e-16*x+1.0 并且这里也能得到该牛顿插值多项式的在[-1,1]上的图形,并和原函数进行对比(见Fig.1)。 Fig.1 牛顿插值多项式(n=10)函数和原函数图形 从图形中我们可以明显的观察出插值函数在两端点处发生了剧烈的波动,产生了极大的误差,即龙格现象,当n=20时,这一现象将更加明显。 1.2 当n=20时: 对n=10的代码进行修改就可以得到n=20时的代码。将“x1=-1:0.2:1;”改为“x1=-1:0.1:1;”即可。运行程序,我们得到n=20时的牛顿插值多项式,结果为:P20(x)= 260188.0*x^20 - 1.0121e6*x^18 + 2.6193e-12*x^17 + 1.6392e6*x^16 + 2.248e-11*x^15 - 1.4429e6*x^14 - 4.6331e-11*x^13 + 757299.0*x^12 + 1.7687e-11*x^11 - 245255.0*x^10 + 2.1019e-11*x^9 + 49318.0*x^8 + 3.5903e-12*x^7 - 6119.2*x^6 - 1.5935e-12*x^5 + 470.85*x^4 + 1.3597e-14*x^3 - 24.143*x^2 - 1.738e-14*x + 1.0 同样的,这里得到了该牛顿插值多项式的在[-1,1]上的图形,并和原函数进行对比(见Fig.2)。

三次样条插值作业题

例1 设)(x f 为定义在[0,3]上的函数,有下列函数值表: 且2.0)('0=x f ,1)('3-=x f ,试求区间[0,3]上满足上述条件的三次样条插值函数)(x s 本算法求解出的三次样条插值函数将写成三弯矩方程的形式: ) ()6()() 6()(6)(6)(211123 13 1j j j j j j j j j j j j j j j j x x h h M y x x h h M y x x h M x x h M x s -- + -- + -+ -= +++++其中,方程中的系数 j j h M 6, j j h M 61+,j j j j h h M y )6(2- , j j j j h h M y ) 6(211++- 将由Matlab 代码中的变量Coefs_1、Coefs_2、Coefs_3以及Coefs_4的值求出。 以下为Matlab 代码: %============================= % 本段代码解决作业题的例1 %============================= clear all clc % 自变量x 与因变量y ,两个边界条件的取值 IndVar = [0, 1, 2, 3]; DepVar = [0, 0.5, 2, 1.5]; LeftBoun = 0.2; RightBoun = -1; % 区间长度向量,其各元素为自变量各段的长度 h = zeros(1, length(IndVar) - 1); for i = 1 : length(IndVar) - 1 h(i) = IndVar(i + 1) - IndVar(i); end % 为向量μ赋值

数值分析作业-三次样条插值

数值计算方法作业 实验4.3 三次样条差值函数 实验目的: 掌握三次样条插值函数的三弯矩方法。 实验函数: dt e x f x t ? ∞ -- = 2 221)(π 实验内容: (1) 编程实现求三次样条插值函数的算法,分别考虑不同的边界条件; (2) 计算各插值节点的弯矩值; (3) 在同一坐标系中绘制函数f(x),插值多项式,三次样条插值多项式的曲线 比较插值结果。 实验4.5 三次样条差值函数的收敛性 实验目的: 多项式插值不一定是收敛的,即插值的节点多,效果不一定好。对三次样条插值函数如何呢?理论上证明三次样条插值函数的收敛性是比较困难的,通过本实验可以证明这一理论结果。 实验内容: 按照一定的规则分别选择等距或非等距的插值节点,并不断增加插值节点的个数。 实验要求: (1) 随着节点个数的增加,比较被逼近函数和三样条插值函数的误差变化情 况,分析所得结果并与拉格朗日插值多项式比较; (2) 三次样条插值函数的思想最早产生于工业部门。作为工业应用的例子,考

虑如下例子:某汽车制造商根据三次样条插值函数设计车门曲线,其中一 算法描述: 拉格朗日插值: 错误!未找到引用源。 其中错误!未找到引用源。是拉格朗日基函数,其表达式为:() ∏ ≠=--=n i j j j i j i x x x x x l 0) ()( 牛顿插值: ) )...()(](,...,,[.... ))(0](,,[)0](,[)()(1102101210100----++--+-+=n n n x x x x x x x x x x f x x x x x x x f x x x x f x f x N 其中????? ?? ?? ?????? --=--= --= -)/(]),...,[],...,[(]...,[..],[],[],,[)()(],[01102110x x x x x f x x x f x x x f x x x x f x x f x x x f x x x f x f x x f n n n n i k j i k j k j i j i j i j i 三样条插值: 所谓三次样条插值多项式Sn(x)是一种分段函数,它在节点Xi(a

三次样条插值方法的应用

CENTRAL SOUTH UNIVERSITY 数值分析实验报告

三次样条插值方法的应用 一、问题背景 分段低次插值函数往往具有很好的收敛性,计算过程简单,稳定性好,并且易于在在电子计算机上实现,但其光滑性较差,对于像高速飞机的机翼形线船体放样等型值线往往要求具有二阶光滑度,即有二阶连续导数,早期工程师制图时,把富有弹性的细长木条(即所谓的样条)用压铁固定在样点上,在其他地方让他自由弯曲,然后沿木条画下曲线,称为样条曲线。样条曲线实际上是由分段三次曲线并接而成,在连接点即样点上要求二阶导数连续,从数学上加以概括就得到数学样条这一概念。下面我们讨论最常用的三次样条函数及其应用。 二、数学模型 样条函数可以给出光滑的插值曲线(面),因此在数值逼近、常微分方程和偏微分方程的数值解及科学和工程的计算中起着重要的作用。 设区间[]b ,a 上给定有关划分b x x n =<<<= 10x a ,S 为[]b ,a 上满足下面条件的函数。 ● )(b a C S ,2∈; ● S 在每个子区间[]1,+i i x x 上是三次多项式。 则称S 为关于划分的三次样条函数。常用的三次样条函数的边界条件有三种类型: ● Ⅰ型 ()()n n n f x S f x S ''0'',==。 ● Ⅱ型 ()()n n n f x S f x S ''''0'''',==,其特殊情况为()()0''''==n n x S x S 。 ● Ⅲ型 ()() 3,2,1,0,0==j x S x S n j j ,此条件称为周期样条函数。 鉴于Ⅱ型三次样条插值函数在实际应用中的重要地位,在此主要对它进行详细介绍。 三、算法及流程 按照传统的编程方法,可将公式直接转换为MATLAB 可是别的语言即可;另一种是运用矩阵运算,发挥MATLAB 在矩阵运算上的优势。两种方法都可以方便地得到结果。方法二更直观,但计算系数时要特别注意。这里计算的是方法一的程序,采用的是Ⅱ型边界条件,取名为spline2.m 。 Matlab 代码如下: function s=spline2(x0,y0,y21,y2n,x) %s=spline2(x0,y0,y21,y2n,x) %x0,y0 are existed points,x are insert points,y21,y2n are the second

试求三次样条插值S(X)

给定数据表如下: 试求三次样条插值S(X),并满足条件: i)S’(0.25)=1.0000, S’(0.53)-0.6868; ii) S”(0.25)= S”(0.53)=0; 解: 由给定数据知: h0 =0.3-0.25 - 0.05 , h 1=0.39-0.30-0.09 h 2=0.45-0.39-0.06, h 3=0.53-0.45-0.08 由μ i=h i/(h i1+h i), λ i= h i/(h i1+h i) 得: μ1= 5/14 ; λ 1= 9/14 μ2= 3/5 ; λ 2= 2/5 μ3= 3/7 ; λ 3=4/7 0.25 0.5000 ﹨ ﹨ 1.0000 ∕﹨ 0.25 0.5000 ∕ -0.9200-f[x 0,x 0, x 1 ] ﹨∕ 0.9540 ∕﹨ 0.30 0.5477 -0.7193-f[x 0,x 1,x 2 ] ﹨∕

0.8533 ∕﹨ 0.39 0.6245 -0.5440-f[x1,x2,x 3 ] ﹨∕ 0.7717 ∕﹨ 0.45 0.6708 -0.4050-f[x 2,x 3,x 4 ] ﹨∕ 0.7150 ∕﹨ 0.53 0.7280 -0.3525-f[x 3,x 4,x 5 ] ﹨∕ 0.6868 ∕ 0.53 0.7280 i)已知一节导数边界条件,弯矩方程组 ┌┐┌┐ │ 2 1 │┌M 0 ┐│-0.9200 ︳ ︳5/14 2 9/14 ︳︳M ︳︳-0.7193 ︳ 1 ︳3/5 2 2/5 ︳︳M 2 ︳_6 ︳-0.5440︳ ︳ 3/7 2 4/7 ︳︳M ︳︳-0.4050 ︳ 3

(精选)三次样条插值的MATLAB实现

MATLAB 程序设计期中考查 在许多问题中,通常根据实验、观测或经验得到的函数表或离散点上的信息,去研究分析函数的有关特性。其中插值法是一种最基本的方法,以下给出最基本的插值问题——三次样条插值的基本提法: 对插值区间[]b a ,进行划分:b x x x a n ≤

关于三次样条插值函数的学习报告(研究生)资料

学习报告—— 三次样条函数插值问题的讨论 班级:数学二班 学号:152111033 姓名:刘楠楠

样条函数: 由一些按照某种光滑条件分段拼接起来的多项式组成的函数;最常用的样条函数为三次样条函数,即由三次多项式组成,满足处处有二阶连续导数。 一、三次样条函数的定义: 对插值区间[,]a b 进行划分,设节点011n n a x x x x b -=<< <<=,若 函数2()[,]s x c a b ∈在每个小区间1[,]i i x x +上是三次多项式,则称其为三次样条函数。如果同时满足()()i i s x f x = (0,1,2)i n =,则称()s x 为()f x 在 [,]a b 上的三次样条函数。 二、三次样条函数的确定: 由定义可设:101212 1(),[,] (),[,]()(),[,] n n n s x x x x s x x x x s x s x x x x -∈??∈?=???∈?其中()k s x 为1[,]k k x x -上的三次 多项式,且满足11(),()k k k k k k s x y s x y --== (1,2,,k n = 由2()[,]s x C a b ∈可得:''''''()(),()(),k k k k s x s x s x s x -+-+== 有''1()(),k k k k s x s x -++= ''''1()(),(1 ,2,,1)k k k k s x s x k n -+ +==-, 已知每个()k s x 均为三次多项式,有四个待定系数,所以共有4n 个待定系数,需要4n 个方程才能求解。前面已经得到22(1)42n n n +-=-个方程,因此要唯一确定三次插值函数,还要附加2个条件,一般上,实际问题通常对样条函数在端点处的状态有要求,即所谓的边界条件。 1、第一类边界条件:给定函数在端点处的一阶导数,即 ''''00(),()n n s x f s x f == 2、第二类边界条件:给定函数在端点处的二阶导数,即

matlab_牛顿插值法_三次样条插值法

(){} 2 1 ()(11),5,10,20: 1252 1()1,(0,1,2,,)()2,(0,1,2,,)() ()2 35,20:1100 (i i i i n n k k k Newton f x x n x f x x i i n f x n x y i n Newton N x S x n x k y f x = -≤≤=+=-+====-+ = 题目:插值多项式和三次样条插值多项式。已知对作、计算函数在点处的值;、求插值数据点 的插值多项式和三次样条插值多项式;、对计算和相应的函数值),()() (1,2,,99)4:()max ()()max ()n k n k n k n k n k n k k k N x S x k E N y N x E S y S x ==-=- 和; 、计算,; 解释你所得到的结果。 算法组织: 本题在算法上需要解决的问题主要是:求出第二问中的Newton 插值多项式 )(x N n 和三次样条插值多项式()n S x 。如此,则第三、四问则迎刃而解。计算两 种插值多项式的算法如下: 一、求Newton 插值多项式)(x N n ,算法组织如下: Newton 插值多项式的表达式如下: )())(()()(110010--???--+???+-+=n n n x x x x x x c x x c c x N 其中每一项的系数c i 的表达式如下: 1102110) ,,,(),,,(),,,(x x x x x f x x x f x x x f c i i i i i -???-???= ???=- 根据i c 以上公式,计算的步骤如下: ?? ??? ?? ?????+??????? ???????????----) ,,,,(1) ,,,(),,,,(),(,),,(2)(,),(),(11101111011010n n n n n n n n x x x x f n x x x f x x x f n x x f x x f x f x f x f 、计算、计算、计算、计算 二、求三次样条插值多项式)(x S n ,算法组织如下:

三次样条插值自然边界条件

例:已知一组数据点,编写一程序求解三次样条插值函数满足 并针对下面一组具体实验数据 0.25 0.3 0.39 0.45 0.53 0.5000 0.5477 0.6245 0.6708 0.7280 求解,其中边界条件为. 1)三次样条插值自然边界条件源程序: function s=spline3(x,y,dy1,dyn) %x为节点,y为节点函数值,dy1,dyn分别为x=0.25,0.53处的二阶导 m=length(x);n=length(y); if m~=n error('x or y输入有误') return end h=zeros(1,n-1); h(n-1)=x(n)-x(n-1); for k=1:n-2 h(k)=x(k+1)-x(k); v(k)=h(k+1)/(h(k+1)+h(k)); u(k)=1-v(k); end g(1)=3*(y(2)-y(1))/h(1)-h(1)/2*dy1; g(n)=3*(y(n)-y(n-1))/h(n-1)+h(n-1)/2*dyn; for i=2:n-1 g(i)=3*(u(i-1)*(y(i+1)-y(i))/h(i)+v(i-1)*(y(i)-y(i-1))/h(i-1)); end for i=2:n-1; A(i,i-1)=v(i-1); A(i,i+1)=u(i-1); end A(n,n-1)=1; A(1,2)=1; A=A+2*eye(n); M=zhuigf(A,g); %调用函数,追赶法求M fprintf('三次样条(三对角)插值的函数表达式\n'); syms X;

for k=1:n-1 fprintf('S%d--%d:\n',k,k+1); s(k)=(h(k)+2*(X-x(k)))./h(k).^3.*(X-x(k+1)).^2.*y(k)... +(h(k)-2*(X-x(k+1)))./h(k).^3.*(X-x(k)).^2.*y(k+1)... +(X-x(k)).*(X-x(k+1)).^2./h(k).^2*M(k)+(X-x(k+1)).*... (X-x(k)).^2./h(k).^2*M(k+1); end s=s.'; s=vpa(s,4); %画三次样条插值函数图像 for i=1:n-1 X=x(i):0.01:x(i+1); st=(h(i)+2*(X-x(i)))./(h(i)^3).*(X-x(i+1)).^2.*y(i)... +(h(i)-2.*(X-x(i+1)))./(h(i)^3).*(X-x(i)).^2.*y(i+1)... +(X-x(i)).*(X-x(i+1)).^2./h(i)^2*M(i)+(X-x(i+1)).*... (X-x(i)).^2./h(i)^2*M(i+1); plot(x,y,'o',X,st); hold on End plot(x,y); grid on %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %调用的函数: %追赶法 function M=zhuigf(A,g) n=length(A); L=eye(n); U=zeros(n); for i=1:n-1 U(i,i+1)=A(i,i+1); end U(1,1)=A(1,1); for i=2:n L(i,i-1)=A(i,i-1)/U(i-1,i-1); U(i,i)=A(i,i)-L(i,i-1)*A(i-1,i); end Y(1)=g(1); for i=2:n Y(i)=g(i)-L(i,i-1)*Y(i-1); end M(n)=Y(n)/U(n,n); for i=n-1:-1:1 M(i)=(Y(i)-A(i,i+1)*M(i+1))/U(i,i);

MATLAB三次样条插值之三弯矩法

MATLAB三次样条插值之三弯矩法 首先说这个程序并不完善,为了实现通用(1,2,…,n)格式解题,以及为调用追赶法程序,没有针对节点数在三个以下的情况进行分类讨论。希望能有朋友给出更好的方法。 首先,通过函数sanwanj得到方程的系数矩阵,即追赶法方程的四个向量参数,接下来调 用追赶法(在intersanwj函数中),得到三次样条分段函数系数因子,然后进行多项式合并 得到分段函数的解析式,程序最后部分通过判断输入值的区间自动选择对应的分段函数并计算 改点的值。附:追赶法程序chase %%%%%%%%%%%%%% function [newv,w,newu,newd]=sanwj(x,y,x0,y0,y1a,y1b)?%三弯矩样 条插值?%将插值点分两次输入,x0y0单独输入?% 边值条件a的二阶导数 y1a 和b 的二阶导数y1b,这里建议将y1a和y1b换成y2a和y2b,以便于和三转角代码相区别 ?n=length(x);m=length(y); if m~=n?error('x or y 输入有误,再来'); end?v=ones(n-1,1);u=ones(n-1,1);d=zeros(n-1,1);?w=2*o nes(n+1);?h0=x(1)-x0;?h=zeros(n-1,1); for k=1:n-1?h(k)=x(k+1)-x(k);?end v(1)=h0/(h0+h(1)); u(1)=1-v(1); d(1)=6*((y(2)-y(1))/h(1)-(y(1)-y0)/h0)/(h0+h(1));?% for k=2:n-1?v(k)=h(k-1)/(h(k-1)+h(k));?u(k)=1-v(k);?d(k)= 6*((y(k+1)-y(k))/h(k)-(y(k)-y(k-1))/h(k-1))/(h(k-1)+h(k)); end newv=[v;1];?newu=[1;u]; d0=6*((y(1)-y0)/h0-y1a)/h0; d(n)=6*(y1b-(y(n)-y(n-1))/h(n-1))/h(n-1); newd=[d0;d]; %%%%%%%%%%%% function intersanwj(x,y,x0,y0,y1a,y1b) %三弯矩样条插值?%第一部分?n=length(x);m=length(y); if m~=n?error('xory 输入有误,再来'); end?%重新定义h?h=zeros(n,1); h(1)=x(1)-x0; for k=2:n h(k)=x(k)-x(k-1);?end %sptep1调用三弯矩函数?[a,b,c,d]=sanwj(x,y,x0,y0,y1a,y1b);

数值分析实验报告-插值、三次样条(教育教学)

实验报告:牛顿差值多项式&三次样条 问题:在区间[-1,1]上分别取n=10、20用两组等距节点对龙格函数2 1()25f x x 作多项式插值及三次样条插值,对每个n 值,分别画出插值函数及()f x 的图形。 实验目的:通过编程实现牛顿插值方法和三次样条方法,加深对多项式插值的理解。应用所编程序解决实际算例。 实验要求: 1. 认真分析问题,深刻理解相关理论知识并能熟练应用; 2. 编写相关程序并进行实验; 3. 调试程序,得到最终结果; 4. 分析解释实验结果; 5. 按照要求完成实验报告。 实验原理: 详见《数值分析 第5版》第二章相关内容。 实验内容: (1)牛顿插值多项式 1.1 当n=10时: 在Matlab 下编写代码完成计算和画图。结果如下: 代码: clear all clc x1=-1:0.2:1; y1=1./(1+25.*x1.^2); n=length(x1); f=y1(:); for j=2:n for i=n:-1:j f(i)=(f(i)-f(i-1))/(x1(i)-x1(i-j+1)); end end syms F x p ; F(1)=1;p(1)=y1(1); for i=2:n F(i)=F(i-1)*(x-x1(i-1)); p(i)=f(i)*F(i);

end syms P P=sum(p); P10=vpa(expand(P),5); x0=-1:0.001:1; y0=subs(P,x,x0); y2=subs(1/(1+25*x^2),x,x0); plot(x0,y0,x0,y2) grid on xlabel('x') ylabel('y') P10即我们所求的牛顿插值多项式,其结果为:P10(x)=-220.94*x^10+494.91*x^8-9.5065e-14*x^7-381.43*x^6-8.504e-14*x^5+123.36*x^4+2.0202e-1 4*x^3-16.855*x^2-6.6594e-16*x+1.0 并且这里也能得到该牛顿插值多项式的在[-1,1]上的图形,并和原函数进行对比(见Fig.1)。 Fig.1 牛顿插值多项式(n=10)函数和原函数图形 从图形中我们可以明显的观察出插值函数在两端点处发生了剧烈的波动,产生了极大的误差,即龙格现象,当n=20时,这一现象将更加明显。 1.2 当n=20时: 对n=10的代码进行修改就可以得到n=20时的代码。将“x1=-1:0.2:1;”改为“x1=-1:0.1:1;”即可。运行程序,我们得到n=20时的牛顿插值多项式,结果为:P20(x)= 260188.0*x^20 - 1.0121e6*x^18 + 2.6193e-12*x^17 + 1.6392e6*x^16 + 2.248e-11*x^15 - 1.4429e6*x^14 - 4.6331e-11*x^13 + 757299.0*x^12 + 1.7687e-11*x^11 - 245255.0*x^10 + 2.1019e-11*x^9 + 49318.0*x^8 + 3.5903e-12*x^7 - 6119.2*x^6 - 1.5935e-12*x^5 + 470.85*x^4 + 1.3597e-14*x^3 - 24.143*x^2 - 1.738e-14*x + 1.0 同样的,这里得到了该牛顿插值多项式的在[-1,1]上的图形,并和原函数进行对比(见Fig.2)。

实验四三次样条插值Word版

实验四三次样条插值的应用 一、问题描述 The upper portion of this noble beast is to be approximated using clamped cubic spline interpolants. The curve is drawn on a grid from which the table is constructed. Use Algorithm 3.5 to construct the three clamped cubic splines. 二、模型建立 三次样条插值 给定一个列表显示的函数 yi=y(xi),i=0,1,2,...,N-1。特别注意在xj和xj+1之间的一个特殊的区间。该区间的线性插值公式为:

(3.3.1)式和(3.3.2)式是拉格朗日插值公式(3.1.1)的特殊情况。 因为它是(分段)线性的,(3.3.1)式在每一区间内的二阶导数为零,在横坐标为xj处的二阶导数不定义或无限。三次样条插值的目的就是要得到一个内插公式,不论在区间内亦或其边界上,其一阶导数平滑,二阶导数连续。 做一个与事实相反的个假设,除yi的列表值之外,我们还有函数二阶导数y"的列表值,即一系列的yi"值,则在每个区间内,可以在(3.3.1)式的右边加上一个三次多项式,其二阶导数从左边的yj"值线性变化到右边的yj+1"值,这么做便得到了所需的连续二阶导数。如果还将三次多项式构造在xj和xj+1处为零,则不会破坏在终点xj和xj+1处与列表函数值yj和yj+1的一致性。 进行一些辅助计算便可知,仅有一种办法才能进行这种构造,即用 注意,(3.3.3)式和(3.3.4)式对自变量x的依赖,是完全通过A和B对x的线性依赖,以及C和D(通过A和B)对x的三次依赖而实现。可以很容易地验证,y"事实上是该插值多项式的二阶导数。使用ABCD的定义对x求(3.3.3)式的导数,计算dA/dx dB/dx dC/dx dD/dx,结果为一阶导数

数值分析课程设计--三次样条插值

《数值分析》课程设计 三次样条插值算法 院(系)名称信息工程学院 专业班级09普本信计1班 学号 学生姓名 指导教师

数值分析课程设计评阅书

课程设计任务书 2008—2009学年第二学期 专业班级:09普本信计1班学号:姓名: 课程设计名称:数值分析 设计题目:三次样条插值 完成期限:自2012 年 6 月8 日至2012 年 6 月13 日共 1 周 设计依据、要求及主要内容: 一、设计目的 熟练掌握三次样条插值算法的原理和推导过程,并且能够应用Matlab软件编写相应的程序和使用Matlab软件函数库软件。 二、设计要求 (1)用Matlab函数库中相应函数对选定的问题,求出具有一定精度的结果。 (2)使用所用的方法编写Matlab程序求解,对数值结果进行分析。 (3)对于使用多个方法解同一问题的,在界面上设计成菜单形式。 三、设计内容 首先构造三次样条插值函数的定义和一般特征,并对实例问题进行实例分析,并总结 四、参考文献 [1] 黄明游,冯果忱.数值分析[M].北京:高等教育出版社,2008. [2]马东升,雷勇军.数值计算方法[M].北京:机械工业出版社,2006. [3] 石博强,赵金.MATLAB数学计算与工程分析范例教程[M].北京:中国铁道出版社.2005. [4]郝红伟,MATLAB 6,北京,中国电力出版社,2001 [5]姜健飞,胡良剑,数值分析及其MATLAB实验,科学出版社,2004 [6]薛毅,数值分析实验,北京工业大学出版社,2005 计划答辩时间:2012年6月18日

指导教师(签字):教研室主任(签字):批准日期:年月

数值分析课程设计(三次样条插值)

《数值分析课程设计》 报告 专业: 学号: 学生姓名: 指导教师:

7.掌握三次样条插值函数的构造方法,体会三次样条插值函数对被逼近函数的近似。 三次样条插值函数边界条件由实际问题对三次样条插值在端点的状态要求给出。以第1 边界条件为例, 用节点处二阶导数表示三次样条插值函数,用追赶法求解相关方程组。通过Matlab 编制三次样条函数的通用程序,可直接显示各区间段三次样条函数体表达式,计算出已给点插值并显示各区间分段曲线图。 引言 分段低次样条插值虽然计算简单、稳定性好、收敛性有保证且易在电子计算机上实现,但只能保证各小段曲线在连接处的连续性,不能保证整件曲线的光滑性。利用样条插值,既可保持分段低次插值多项式,又可提高插值函数光滑性。故给出分段三次样条插值的构造过程算法步骤,利用Matlab软件编写三次样条插值函数通用程序,并通过数值算例证明程序的正确性。 三次样条函数的定义及特征 定义:设[a,b] 上有插值节点,a=x1<x2<…x n=b,对应函数值为y1,y2,?y n。若函数S(x) 满足S(x j) =y j (j =1,2, ?,n ),S(x) 在[x j,x j+1] (j =1,2,?,n-1)上都是不高于三的多项式(为了与其对应j 从1 开始,在Matlab 中元素脚标从1 开始)。当S(x) 在[a,b] 具有二阶连续导数。则称S(x) 为三次样条插值函数。要求S(x) 只需在每个子区间[x j,x j+1] 上确定1 个三次多项式,设为: Sj(x)=ajx3+bjx2+cjx+dj, (j=1,2,?,n-1) (1) 其中a j,b j,c j,d j 待定,并要使它满足: S(x j)=y j, S(x j-0)=S(x j+0), (j=2,?,n-1) (2) S'(x j-0)=S'(x j+0), S"(x j-0)=S"(x j+0), (j=2,?,n-1) (3) 式(2)、(3)共给出n+3(n-2)=4n-6 个条件, 需要待定4(n-1) 个系数,因此要唯一确定三次插值函数,还要附加2 个边界条件。通常由实际问题对三次样条插值在端点的状态要求给出。常用边界的条件有以下3 类。 第1 类边界条件:给定端点处的一阶导数值,S'(x1)=y1',S'(x n)=y n'。 第 2 类边界条件:给定端点处的二阶导数值,S"(x1)=y1",S"(x n)=y n"。特殊情况y1"=y n"=0,称为自然边界条件。 第3 类边界条件是周期性条件,如果y=f(x)是以b-a 为周期的函数,于是S(x) 在端点处满足条件S'(x1+0)=S'(x n-0),S"(x+0)=S"(x n-0)。 下以第1 边界条件为例,利用节点处二阶导数来表示三次样条插值函数,给出具体的推导过程。 2 三次样条插值函数的推导过程 注意到S(x) 在[x j, x j+1](j=1,2,?,n-1)上是三次多项式,于是S"(x)在[x j, x j+1] 上是一次多项式,如果S"(x) 在[x j,x j+1](j=1,2,?,n-1)两端点上的值已知,设S"(x j)=M j,S"(x j+1)=M j+1,其中h j =x j+1-x j,对S"(x) 进行两次积分,则得到1 个具有2个任意常数A j,B j 的S(x) 表达式。对S"(x) 求两次积分

三次样条插值的C程序(很全啊)

三次样条插值C/C++程序(自己整理的) 具体推导看书<<数值分析>> code: #include using namespace std; const int MAXN = 100; int n; double x[MAXN], y[MAXN]; //下标从0..n double alph[MAXN], beta[MAXN], a[MAXN], b[MAXN]; double h[MAXN]; double m[MAXN]; //各点的一阶导数; inline double sqr(double pa) { return pa * pa; } double sunc(double p, int i) { return (1 + 2 * (p - x[i]) / (x[i + 1] - x[i])) * sqr((p - x[i + 1]) / (x[i + 1] - x[i])) * y[i] + (1 + 2 * (p - x[i + 1]) / (x[i] - x[i + 1])) * sqr((p - x[i]) / (x[i + 1] - x[i])) * y[i + 1] + (p - x[i]) * sqr((p - x[i + 1]) / (x[i] - x[i + 1])) * m[i] + (p - x[i + 1]) * sqr((p - x[i]) / (x[i + 1] - x[i])) * m[i + 1]; } int main() { int i, j;

freopen("threeInsert.in", "r", stdin); scanf("%d", &n); for (i = 0; i <= n; i++) scanf("%lf%lf", &x[i], &y[i]); // scanf("%lf%lf", &m[0], &m[n]); for (i = 0; i <= n - 1; i++) h[i] = x[i + 1] - x[i]; //第一种边界条件 //alph[0] = 0; alph[n] = 1; beta[0] = 2 * m[0]; beta[n] = 2 * m[n]; //第二种边界条件 alph[0] = 1; alph[n] = 0; beta[0] = 3 * (y[1] - y[0]) / h[0]; beta[n] = 3 * (y[n] - y[n - 1] / h[n - 1]); for (i = 1; i <= n - 1; i++) { alph[i] = h[i - 1] / (h[i - 1] + h[i]); beta[i] = 3 * ((1 - alph[i]) * (y[i] - y[i - 1]) / h[i - 1] + alph[i] * (y[i + 1] - y[i]) / h[i]); } a[0] = - alph[0] / 2; b[0] = beta[0] / 2; for (i = 1; i <= n; i++) { a[i] = - alph[i] / (2 + (1 - alph[i]) * a[i - 1]); b[i] = (beta[i] - (1 - alph[i]) * b[i - 1]) / (2 + (1 - alph[i]) * a[i - 1]); } m[n + 1] = 0; for (i = n; i >= 0; i--) { m[i] = a[i] * m[i + 1] + b[i]; } scanf("%lf", &xx); for (i = 0; i < n; i++) { if (xx >= x[i] && xx <= x[i + 1]) break ; } printf("%lf\n", sunc(xx, i));

相关主题