问题描述
我有一个简单的一阶微分方程组,需要在Matlab中求解。看起来像这样:
I have a simple system of 1st-order differential equations to be solved in Matlab. It looks like the following:
function passing
y0 = [0; 0];
t = 0:0.05:1;
y = myprocedure(@myfunc,0.05,t,y0);
myans = y'
end
function f = myfunc(t,y)
f = [-y(1) + y(2);
-0.8*t + y(2)];
end
function y=myprocedure(f,h,t,y0)
n = length(t);
y = zeros(length(y0),n);
y(:,1) = y0;
for i=1:n-1
k1 = f(t(i),y(:,i));
k2 = f(t(i)+h/2, y(:,i)+h/2*k1);
k3 = f(t(i)+h/2, y(:,i)+h/2*k2);
k4 = f(t(i)+h, y(:,i)+h*k3);
y(:,i+1) = y(:,i)+h/6*(k1+2*k2+2*k3+k4);
end
end
因此,在运行passing.m文件之后,我结果为:
So, after running the passing.m file, I have the result:
>> passing
myans =
0 0
-0.0000 -0.0010
-0.0001 -0.0041
-0.0005 -0.0095
-0.0011 -0.0171
-0.0021 -0.0272
-0.0036 -0.0399
-0.0058 -0.0553
-0.0086 -0.0735
-0.0123 -0.0946
-0.0169 -0.1190
-0.0225 -0.1466
-0.0293 -0.1777
-0.0374 -0.2124
-0.0469 -0.2510
-0.0579 -0.2936
-0.0705 -0.3404
-0.0849 -0.3917
-0.1012 -0.4477
-0.1196 -0.5086
-0.1402 -0.5746
现在,我正在尝试将passing.m代码转换为Fortran90。我确实做了很多尝试,但是我仍然迷失了方向,特别是在执行数组初始化并将函数传递给其他函数时
Now, I am trying converting the passing.m code to Fortran 90. I did try lots of things, but I am still lost -- particularly in doing array initializations and passing functions to other functions.
任何帮助都将受到赞赏。谢谢!
Any help is appreciated. Thanks!
==编辑:
我成功地在Fortran 90中复制了上面的Matlab代码。不知道如何构造指针,但是接口语句似乎有效。如果您查看代码并提供一些输入,我将不胜感激。
I succeeded replicating the above Matlab code in Fortran 90. I still don't know how to construct pointers, but the "interface" statement seems to work. I would appreciate it if you look at the code and provide some input. Thanks.
module odemodule
implicit none
contains
function odef(a,b)
implicit none
real::a
real::b(2)
real::odef(2)
odef(1) = -b(1) + b(2)
odef(2) = -0.8*a + b(2)
end function odef
subroutine rk4(f,h,t,y0,y)
implicit none
real,dimension(2,21)::y
real,dimension(2)::k1,k2,k3,k4
real::h
real::t(21)
real::y0(2)
integer::i
interface
function f(a,b)
real::a
real::b(2), f(2)
end function f
end interface
y(1,1)=y0(1)
y(2,1)=y0(2)
do i=1,20
k1 = f(t(i),y(:,i))
k2 = f(t(i)+h/2, y(:,i)+h/2*k1)
k3 = f(t(i)+h/2, y(:,i)+h/2*k2)
k4 = f(t(i)+h, y(:,i)+h*k3)
y(:,i+1) = y(:,i)+h/6*(k1+2*k2+2*k3+k4)
end do
end subroutine rk4
end module odemodule
program passing
use odemodule
implicit none
real,parameter::dt=0.05
real::yinit(2)
real::y(2,21)
integer::i
real::t(21)
t(1)=0.0
do i=2,21
t(i)=t(i-1)+dt
end do
yinit(1)=0
yinit(2)=0
call rk4(odef,dt,t,yinit,y)
do i=1,21
write(*,100) y(1,i), y(2,i)
enddo
100 format(f7.4,3x,f7.4)
end program passing
推荐答案
在Fortran中选择要传递给其他过程(子例程或函数)的函数的最佳方法是使用过程指针。这样,您可以以一般方式编写过程并使用特定功能调用它。以下是一些示例:和
The best way in Fortran to select functions to pass to other procedures (subroutine or functions) is to use procedure pointers. That way you can write the procedure in a general manner and invoke it with a specific function. Here are some examples: How to alias a function name in Fortran and Function pointer arrays in Fortran
有很多初始化错误的方法。例如,可以将所有元素初始化为相同的值,例如,
There are many ways to initialize arrrays. For example, you can initialize all elements to the same value, e.g.,
array = 0.0
请参见
这篇关于Fortran |将函数作为其他函数中的参数传递的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!