计算物理学(数值分析)上机实验答案5、常微分方程初值问题的数值解法

该博客详细介绍了如何使用MATLAB进行常微分方程初值问题的数值解法,包括欧拉法、自适应欧拉法、向后欧拉法、四阶龙格-库塔法以及亚当斯方法。通过实例展示了不同方法的编程实现和误差分析,旨在帮助读者熟悉和掌握这些数值解法。
摘要由CSDN通过智能技术生成

实验五、常微分方程初值问题的数值解法

​ 常微分方程的求解问题在实践中经常遇到,因此研究常微分方程的数值解法就很有必要。欧拉方法是最简单、最基本的方法,利用差商代替微商,就可得到一系列欧拉公式。这些公式形式简洁,易于编程计算,但精度较低,可方便用于精度要求不高的近似计算。龙格-库塔方法是利用区间上多个点的斜率值的加权平均的思想,得出的高精度的计算公式。特别是四阶龙格-库塔公式,易于编程计算,精度较高,是常用的工程计算方法。线性多步方法是在用插值多项式代替被积函数的基础上构造的,它可利用前面若干步计算结果的信息,使计算结果提高精度,其中较常用的是四阶阿当姆斯方法。

一、实验目的

1、 熟悉求解常微分方程初值问题的有关方法和理论,主要是改进欧拉法、四阶龙格-库塔法;

2、会编制上述方法的计算程序,包括求解微分方程组的计算程序;

3、针对实习题编制程序,并上机计算其所需要的结果;

4、 通过对各种求解方法的计算实习,体会各种解法的功能、优缺点及适用场合, 会选取适当的求解方法。

二、算法实例

1.向前欧拉公式的 MATLAB 主程序

例 5.1

​ 用欧拉方法求初值问题的数值解,分别取h = 0.0750,0.0075,并计算误差,画出精确解和数值解的图形。
{ d y d x = x − y , 0 ≤ x ≤ 1 y ∣ x = 0 = 1 \left\{ \begin{array} { c } { \frac { d y } { d x } = x - y , 0 \leq x \leq 1 } \\ { y | _ { x = 0 } = 1 } \end{array} \right. { dxdy=xy,0x1yx=0=1

解:编写并保存名为 Eulerli1.m 的 MATLAB 计算和画图的主程序如下

function P=Eulerli1(x0,y0,b,h)
n=round(fix((b-x0)/h));%取整数
X=zeros(n,1);Y=zeros(n,1); k=1;
X(k)=x0; Y(k)=y0;
for k=1:n
    X(k+1)=X(k)+h;
    Y(k+1)=Y(k)+h*(X(k)-Y(k)); k=k+1;
end
y=X-1+2*exp(-X); plot(X,Y,'mp',X,y,'b-')
grid
xlabel('自变量 X'), ylabel('因变量 Y')
title('用向前欧拉公式求dy/dx=x-y,y(0)=1在[0,1]上的数值解和精确解y=x-1+2 exp(-x)')
legend('h=0.075时,dy/dx=x-y,y(0)=1在[0,1]上的数值解','精确解y=x-1+2 exp(-x)')
jwY=y-Y;xwY=jwY./y;
k1=1:n;k=[0,k1];
P=[k',X,Y,y,jwY,xwY];

在 MATLAB 工作窗口输入下面的程序

x0=0;y0=1;b=1;h=0.0750;
P=Eulerli1(x0,y0,b,h)

在 MATLAB 工作窗口输入下面的程序

h1=0.0075; P1=Eulerli1(x0,y0,b,h1)
legend('h1=0.0075 时,dy/dx=x-y,y(0)=1 在[0,1]上的数值解','精确解 y=x-1+2 exp(-x)')

2.自适应向前欧拉公式的 MATLAB 主程序

function [H,X,Y,k,h,P]=QEuler(funfcn,x0,b,y0,tol)
%初始化.
pow=1/3;
if nargin < 5 | isempty(tol)
    tol = 1e-6;
end;
if nargin < 6 | isempty(trace)
    trace = 0;
end;
x=x0; h=0.0078125*(b-x); y=y0(:);p=128;
H=zeros(p,1);
X=zeros(p,1); Y=zeros(p,length(y)); k=1; X(k)=x;
Y(k,:)=y';
% 绘图.
clc,x,h,y
end
% 主循环.
while (x<b)&(x+h>x)
    if x+h>b
        h=b-x;
    end
    %计算斜率.
    fxy=feval(funfcn,x,y); fxy=fxy(:);
    %计算误差,设定可接受误差.
    delta=norm(h*fxy,'inf');
    wucha=tol*max(norm(y,'inf'),1.0);
    % 当误差可接受时重写解.
    if delta<=wucha
        x=x+h; y=y+h*fxy; k=k+1;
        if k>length(X)
            X=[X;zeros(p,1)]; Y=[Y;zeros(p,length(y))];
            H=[H;zeros(p,1)];
        end
        H(k)=h;X(k)=x;Y(k,:)=y'; plot(X,Y,'rp'), grid
        xlabel('自变量 X'), ylabel('因变量 Y')
        title('用向前欧拉(Euler)公式计算dy/dx=f(x,y),y(x0)=y0在[x0,b]上的数值解')
    end
    %更新步长.
    if delta~=0.0
        h=min(h*8,0.9*h*(wucha/delta)^pow);
    end
end
if (x<b)
    disp('Singularity likely.'), x
end
H=H(1:k);
X=X(1:k);
Y=Y(1:k,:);
n=1:k; P=[n',H,X,Y]

3.向后欧拉方法的 MATLAB 程序

function [X,Y,n,P]=Heuler1(funfcn,x0,b,y0,h,tol)
n=fix((b-x0)/h); X=zeros(n+1,1); Y=zeros(n+1,1);
k=1; X(k)=x0; Y(k,:)=y0; Y1(k,:)=y0;
% 绘图.
clc,x0,h,y0
% 产生初值.
for i=2:n+1
    X(i)=x0+h; Y(i,:)=y0+h*feval(funfcn,x0,y0);
    Y1(i,:)=y0+h*feval(funfcn,X(i),Y(i,:));
    % 主循环.
    Wu=abs(Y1(i,:)-Y(i,:));
    while Wu>tol
        p=Y1(i,:);
        Y1(i,:)=y0+h*feval(funfcn,X(i),p);
        Y(i,:)=p;
    end
    x0=x0+h; y0=Y1(i,:);
    Y(i,:)=y0; plot(X,Y,'ro')
    grid on
    xlabel('自变量 X'), ylabel('因变量 Y')
    title('用向后欧拉公式计算dy/dx=f(x,y),y(x0)=y0在[x0,b]上的数值解')
end
X=X(1:n+1); Y=Y(1:n+1,:); n=1:n+1; P=[n',X,Y]
例 5.2

​ 用向后欧拉公式求解区间[0,2] 上的初值问题 d y d x = − 3 y + 8 x − 7 \frac { d y } { d x } = - 3 y + 8 x - 7 dxdy=3y+8x7

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值