需要将以下 FORTRAN 代码转换为 C++

发布于 2024-09-30 15:13:11 字数 1838 浏览 2 评论 0原文

我是一个非常糟糕的程序员,他们给了我一个程序,据说可以帮助我改进空气动力学硬件。但它是用 Fortran 编写的,我正在尝试使用 MATLAB 来运行这个程序。有什么帮助可以将其转换为 matlab 可以理解的语言吗? (最好是c++)

      program joukow
c

c   computes joukowski airfoil and finds pressure coefficient

c   currently set up for symmetric airfoil with sharp trailing edge

c   and chord length equal to one.

c   profile is written onto prof.dat and cp onto cp.dat

c      implicit real*8(a-h,o-z)

      complex z,zeta,cw
      dimension uz(100),vz(100),xi(100),eta(100),cp(100)
      dimension xout(100),yout(100)
         open(unit=8,file='prof.dat',status='unknown')
         open(unit=9,file='cp.dat',status='unknown')
      b=1.d0
      write(6,98)
      format(2x,'input the radius of the a-circle in z plane')
      read(5,99)a
      format(f10.0)
      xl=2.*a-1.+1./(2.*a-1.)

c      xl=a+1./a

c      chord=2.*xl

      chord=2.+xl
      del=a-b

c      del =0.1d0
      do 50 i=1,100
      ri=i
      theta=6.2832d0*ri/101.d0
      x=-del+a*cos(theta)
      y=a*sin(theta)
      z=cmplx(x,y)
      zeta=z+b**2/z

c

c  xi and eta are coordinates of points on airfoil

c

      xi(i)=real(zeta)

      eta(i)=aimag(zeta)

      cw=(1.-a**2/(z+del)**2)/(1.-b**2/z**2)
c

c  uz and vz are velocity components on the airfoil assuming the free-stream

c  speed is one.
c
      uz(i)=real(cw)
      vz(i)=-aimag(cw)

c

c  xout and yout are airfoil coordinates where the leading edge is at (0,0)

c  and the chordlength is one.

c

      xout(i)=(xl+xi(i))/chord
      yout(i)=eta(i)/chord
      write(8,100)xout(i),yout(i)
      format(2x,2f10.4)
      continue

c

c  now calculate the pressure coefficient cp

c

      write(6,200)
      format(2x,'pressure coefficients')
      do 70 i=1,50
      cp(i)=1.-(uz(i)**2+vz(i)**2)
      write(9,100)xout(i),cp(i)
      continue
      stop
      end

Im a very poor programmer, and i was given a program to supposedly help me on my aerodynamic hw. but its in fortran, and im trying to use MATLAB to run this program. any help on converting it to a language matlab understands? (preferabbly c++)

      program joukow
c

c   computes joukowski airfoil and finds pressure coefficient

c   currently set up for symmetric airfoil with sharp trailing edge

c   and chord length equal to one.

c   profile is written onto prof.dat and cp onto cp.dat

c      implicit real*8(a-h,o-z)

      complex z,zeta,cw
      dimension uz(100),vz(100),xi(100),eta(100),cp(100)
      dimension xout(100),yout(100)
         open(unit=8,file='prof.dat',status='unknown')
         open(unit=9,file='cp.dat',status='unknown')
      b=1.d0
      write(6,98)
      format(2x,'input the radius of the a-circle in z plane')
      read(5,99)a
      format(f10.0)
      xl=2.*a-1.+1./(2.*a-1.)

c      xl=a+1./a

c      chord=2.*xl

      chord=2.+xl
      del=a-b

c      del =0.1d0
      do 50 i=1,100
      ri=i
      theta=6.2832d0*ri/101.d0
      x=-del+a*cos(theta)
      y=a*sin(theta)
      z=cmplx(x,y)
      zeta=z+b**2/z

c

c  xi and eta are coordinates of points on airfoil

c

      xi(i)=real(zeta)

      eta(i)=aimag(zeta)

      cw=(1.-a**2/(z+del)**2)/(1.-b**2/z**2)
c

c  uz and vz are velocity components on the airfoil assuming the free-stream

c  speed is one.
c
      uz(i)=real(cw)
      vz(i)=-aimag(cw)

c

c  xout and yout are airfoil coordinates where the leading edge is at (0,0)

c  and the chordlength is one.

c

      xout(i)=(xl+xi(i))/chord
      yout(i)=eta(i)/chord
      write(8,100)xout(i),yout(i)
      format(2x,2f10.4)
      continue

c

c  now calculate the pressure coefficient cp

c

      write(6,200)
      format(2x,'pressure coefficients')
      do 70 i=1,50
      cp(i)=1.-(uz(i)**2+vz(i)**2)
      write(9,100)xout(i),cp(i)
      continue
      stop
      end

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

时间海 2024-10-07 15:13:11

Matlab 可以很好地理解 Fortran——查看文档。如果这不能满足您的要求,程序中执行任何计算的大部分代码行只需很少的修改即可输入到 Matlab 控制台中。如果你是一个糟糕的程序员,我建议你花时间将程序修改为Matlab而不是C++。如果你没有得到比我现在有时间更好的帮助,我稍后会写更多。

编辑:首先,关于使用 Matlab 中的 Fortran 源文件的一些信息。如果您确实不想(或不能或出于性能原因不这样做)将 Fortran 重写为 Matlab,然后将其转换为 MEX 文件。使用 f2c(或其他任何东西,包括您自己的时间和精力)首先将 Fortran 翻译成 C 或 C++ 对我来说似乎毫无意义。

如果您不喜欢这个想法,这里有一些将 Fortran 转换为 Matlab 的想法。

首先,所有以 C 或 c 开头的行都是注释,因此您不需要翻译它们。从您的代码开始:

  complex z,zeta,cw
  dimension uz(100),vz(100),xi(100),eta(100),cp(100)
  dimension xout(100),yout(100)

这些行声明了许多变量。在 Matlab 中使用变量之前不必声明变量,但有时这样做是有充分理由的。在 Fortran 中也不必这样做,尽管现在普遍认为这是一个坏主意。您可以使用以下语句在 Matlab 中“声明”这些变量:

uz = zeros(100,1); 
vz = zeros(100,1);

通过在 Matlab 中提前声明这些变量,您可以为它们分配一次内存,并避免一些性能降低的问题。

接下来的两行:

     open(unit=8,file='prof.dat',status='unknown')
     open(unit=9,file='cp.dat',status='unknown')

打开几个文件进行输出。它们稍后会在 write 语句中使用 - 忘记它们,改写诸如 save xout 之类的 Matlab 语句。

下一行是 Fortran,但在 Matlab 中是相同的:

  b=1.d0

下一行从控制台获取半径值:

  write(6,98)
  format(2x,'input the radius of the a-circle in z plane')
  read(5,99)a
  format(f10.0)

再次,我建议您忘记这些,只需使用 Matlab 控制台设置 a 的值。更多不需要翻译的 Fortran(尽管我建议您去掉小数点而不跟上 0,或者在它们之间放置一个空格,并且后面的 * -- .* 是 Matlab 中的特定运算符):

  xl=2.*a-1.+1./(2.*a-1.)

  chord=2.+xl
  del=a-b

Fortran do 循环是与 Matlab for 循环相同。重写:

  do 50 i=1,100

正如

for i = 1:100

其他受访者之一所指出的那样,不清楚匹配的结束语句在哪里,您必须弄清楚这一点。请注意,我只是提供 Fortran 到 Matlab 的逐行翻译。它不是写得很好的 Fortran,而且我也没有提供写得很好的 Matlab,我会把它留给你。

这部分不需要翻译:

  ri=i
  theta=6.2832d0*ri/101.d0 
  x=-del+a*cos(theta)
  y=a*sin(theta)

cmplx 是一个 Fortran 函数,它返回一个复数,该复数具有实部 x 和虚部 y:

  z=cmplx(x,y)

在 Matlab 中,这将是 z = x + y * i。 Fortran 使用 ** 进行求幂,Matlab 使用 ^

  zeta=z+b**2/z

等等。

希望有帮助。

Matlab understands Fortran just fine -- check the documentation. And if that doesn't satisfy you, most of the lines in the program which do any computation could be typed into the Matlab console with very little modification. If you are a poor programmer, I suggest that you spend your time modifying the program into Matlab rather than into C++. I'll write more later if you don't get any better help than I have time for right now.

EDIT: first off, some information on using Fortran source files from Matlab. If you really don't want to (or can't or have performance reasons for not doing so) rewrite the Fortran into Matlab then turn it into a MEX file. Using f2c (or anything else, including your own time and effort) to first translate the Fortran into C or C++ seems pointless to me.

If you don't like that idea, here are some ideas on turning Fortran into Matlab.

First, all lines beginning with C or c are comments so you don't need to translate them. Start with your code:

  complex z,zeta,cw
  dimension uz(100),vz(100),xi(100),eta(100),cp(100)
  dimension xout(100),yout(100)

These lines declare a number of variables. You don't have to declare variables before you use them in Matlab but, there are sometimes good reasons to do so. You don't have to in Fortran either, though this is universally considered a bad idea these days. You could 'declare' these variables in Matlab with statements such as:

uz = zeros(100,1); 
vz = zeros(100,1);

By declaring these in advance in your Matlab you allocate memory for them once, and avoid some performance-reducing problems.

The next 2 lines:

     open(unit=8,file='prof.dat',status='unknown')
     open(unit=9,file='cp.dat',status='unknown')

open a couple of files for output. They are used later in write statements - forget them, write Matlab statements such as save xout instead.

The next line is Fortran but identical in Matlab:

  b=1.d0

The next lines get a value for the radius from the console:

  write(6,98)
  format(2x,'input the radius of the a-circle in z plane')
  read(5,99)a
  format(f10.0)

again, I suggest you forget these, just use the Matlab console to set the value of a. More Fortran that doesn't need to be translated (though I suggest you either drop the decimal points without following 0s or put a space between them and the subsequent * -- .* is a specific operator in Matlab):

  xl=2.*a-1.+1./(2.*a-1.)

  chord=2.+xl
  del=a-b

A Fortran do loop is the same as a Matlab for loop. Rewrite:

  do 50 i=1,100

as

for i = 1:100

As one of the other respondents has noted it's not clear where the matching end statement goes, you'll have to figure that out. Note that I'm just offering a line-by-line translation of Fortran into Matlab. It's not well-written Fortran, and I'm not offering well-written Matlab, I'll leave that to you.

This lot doesn't need to be translated:

  ri=i
  theta=6.2832d0*ri/101.d0 
  x=-del+a*cos(theta)
  y=a*sin(theta)

cmplx is a Fortran function which returns a complex number which has real part x and imaginary part y:

  z=cmplx(x,y)

In Matlab this would be z = x + y * i. Fortran uses ** for exponentiation, Matlab uses ^

  zeta=z+b**2/z

and so on and so on.

Hope that helps.

微凉徒眸意 2024-10-07 15:13:11

我使用了 f2matlab,然后进行了一些修改。这是清理后可编译的 fortran90 代码:

program joukow
 !
 !   computes joukowski airfoil and finds pressure coefficient
 !   currently set up for symmetric airfoil with sharp trailing edge
 !   and chord length equal to one.
 !   profile is written onto prof.dat and cp onto cp.dat
 !      implicit real*8(a-h,o-z)
 complex z,zeta,cw
 dimension uz(100),vz(100),xi(100),eta(100),cp(100)
 dimension xout(100),yout(100)
 open(unit=8,file='prof.dat',status='unknown')
 open(unit=9,file='cp.dat',status='unknown')
 b=1.d0
 write(6,98)
98 format(2x,'input the radius of the a-circle in z plane')
 read(5,99)a
99 format(f10.0)
 xl=2.*a-1.+1./(2.*a-1.)
!      xl=a+1./a
!      chord=2.*xl
 chord=2.+xl
 del=a-b
!      del =0.1d0
 do i=1,100
  ri=i
  theta=6.2832d0*ri/101.d0
  x=-del+a*cos(theta)
  y=a*sin(theta)
  z=cmplx(x,y)
  zeta=z+b**2/z
  !
  !  xi and eta are coordinates of points on airfoil
  !
  xi(i)=real(zeta)
  eta(i)=aimag(zeta)
  cw=(1.-a**2/(z+del)**2)/(1.-b**2/z**2)
  !
  !  uz and vz are velocity components on the airfoil assuming the free-stream
  !  speed is one.
  !
  uz(i)=real(cw)
  vz(i)=-aimag(cw)
  !
  !  xout and yout are airfoil coordinates where the leading edge is at (0,0)
  !  and the chordlength is one.
  !
  xout(i)=(xl+xi(i))/chord
  yout(i)=eta(i)/chord
  write(8,100)xout(i),yout(i)
100 format(2x,2f10.4)
 end do
!
!  now calculate the pressure coefficient cp
!
 write(6,200)
200 format(2x,'pressure coefficients')
 do  i=1,50
  cp(i)=1.-(uz(i)**2+vz(i)**2)
  write(9,100) xout(i),cp(i)
 end do
 stop
end program joukow

这是生成的 matlab 代码:

function hw1(varargin)
%
%   computes joukowski airfoil and finds pressure coefficient
%   currently set up for symmetric airfoil with sharp trailing edge
%   and chord length equal to one.
%   profile is written onto prof.dat and cp onto cp.dat
%      implicit real*8(a-h,o-z)

format_99=['%10.0f'];
format_100=[repmat(' ',1,2),repmat('%10.4f',1,2),'\n'];
format_200=[repmat(' ',1,2),'pressure coefficients \n'];

fid_8=fopen('prof.dat','w+');
fid_9=fopen('cp.dat','w+');
b=1.0d0;
a=input('input the radius of the a-circle in z plane');
xl=2..*a-1.+1../(2..*a-1.);
%      xl=a+1./a
%      chord=2.*xl
chord=2.+xl;
del=a-b;
%      del =0.1d0
for i=1:100;
 ri=i;
 theta=6.2832d0.*ri./101.0d0;
 x=-del+a.*cos(theta);
 y=a.*sin(theta);
 z=complex(x,y);
 zeta=z+b.^2./z;
 %
 %  xi and eta are coordinates of points on airfoil
 %
 xi(i)=real(zeta);
 eta(i)=imag(zeta);
 cw=(1.-a.^2./(z+del).^2)./(1.-b.^2./z.^2);
 %
 %  uz and vz are velocity components on the airfoil assuming the free-stream
 %  speed is one.
 %
 uz(i)=real(cw);
 vz(i)=-imag(cw);
 %
 %  xout and yout are airfoil coordinates where the leading edge is at (0,0)
 %  and the chordlength is one.
 %
 xout(i)=(xl+xi(i))./chord;
 yout(i)=eta(i)./chord;
 fprintf(fid_8,format_100,xout(i),yout(i));
end; i=100+1;
%
%  now calculate the pressure coefficient cp
%
fprintf(1,format_200);
for  i=1:50;
 cp(i)=1.-(uz(i).^2+vz(i).^2);
 fprintf(fid_9,format_100, xout(i),cp(i));
end;  i=50+1;
end %program joukow

它们都为我提供了相同的结果。不过,我没有检查算法的正确性,只是转换了代码。

I used f2matlab and a little touching up afterward. Here is the cleaned up and compilable fortran90 code:

program joukow
 !
 !   computes joukowski airfoil and finds pressure coefficient
 !   currently set up for symmetric airfoil with sharp trailing edge
 !   and chord length equal to one.
 !   profile is written onto prof.dat and cp onto cp.dat
 !      implicit real*8(a-h,o-z)
 complex z,zeta,cw
 dimension uz(100),vz(100),xi(100),eta(100),cp(100)
 dimension xout(100),yout(100)
 open(unit=8,file='prof.dat',status='unknown')
 open(unit=9,file='cp.dat',status='unknown')
 b=1.d0
 write(6,98)
98 format(2x,'input the radius of the a-circle in z plane')
 read(5,99)a
99 format(f10.0)
 xl=2.*a-1.+1./(2.*a-1.)
!      xl=a+1./a
!      chord=2.*xl
 chord=2.+xl
 del=a-b
!      del =0.1d0
 do i=1,100
  ri=i
  theta=6.2832d0*ri/101.d0
  x=-del+a*cos(theta)
  y=a*sin(theta)
  z=cmplx(x,y)
  zeta=z+b**2/z
  !
  !  xi and eta are coordinates of points on airfoil
  !
  xi(i)=real(zeta)
  eta(i)=aimag(zeta)
  cw=(1.-a**2/(z+del)**2)/(1.-b**2/z**2)
  !
  !  uz and vz are velocity components on the airfoil assuming the free-stream
  !  speed is one.
  !
  uz(i)=real(cw)
  vz(i)=-aimag(cw)
  !
  !  xout and yout are airfoil coordinates where the leading edge is at (0,0)
  !  and the chordlength is one.
  !
  xout(i)=(xl+xi(i))/chord
  yout(i)=eta(i)/chord
  write(8,100)xout(i),yout(i)
100 format(2x,2f10.4)
 end do
!
!  now calculate the pressure coefficient cp
!
 write(6,200)
200 format(2x,'pressure coefficients')
 do  i=1,50
  cp(i)=1.-(uz(i)**2+vz(i)**2)
  write(9,100) xout(i),cp(i)
 end do
 stop
end program joukow

Here is the resulting matlab code:

function hw1(varargin)
%
%   computes joukowski airfoil and finds pressure coefficient
%   currently set up for symmetric airfoil with sharp trailing edge
%   and chord length equal to one.
%   profile is written onto prof.dat and cp onto cp.dat
%      implicit real*8(a-h,o-z)

format_99=['%10.0f'];
format_100=[repmat(' ',1,2),repmat('%10.4f',1,2),'\n'];
format_200=[repmat(' ',1,2),'pressure coefficients \n'];

fid_8=fopen('prof.dat','w+');
fid_9=fopen('cp.dat','w+');
b=1.0d0;
a=input('input the radius of the a-circle in z plane');
xl=2..*a-1.+1../(2..*a-1.);
%      xl=a+1./a
%      chord=2.*xl
chord=2.+xl;
del=a-b;
%      del =0.1d0
for i=1:100;
 ri=i;
 theta=6.2832d0.*ri./101.0d0;
 x=-del+a.*cos(theta);
 y=a.*sin(theta);
 z=complex(x,y);
 zeta=z+b.^2./z;
 %
 %  xi and eta are coordinates of points on airfoil
 %
 xi(i)=real(zeta);
 eta(i)=imag(zeta);
 cw=(1.-a.^2./(z+del).^2)./(1.-b.^2./z.^2);
 %
 %  uz and vz are velocity components on the airfoil assuming the free-stream
 %  speed is one.
 %
 uz(i)=real(cw);
 vz(i)=-imag(cw);
 %
 %  xout and yout are airfoil coordinates where the leading edge is at (0,0)
 %  and the chordlength is one.
 %
 xout(i)=(xl+xi(i))./chord;
 yout(i)=eta(i)./chord;
 fprintf(fid_8,format_100,xout(i),yout(i));
end; i=100+1;
%
%  now calculate the pressure coefficient cp
%
fprintf(1,format_200);
for  i=1:50;
 cp(i)=1.-(uz(i).^2+vz(i).^2);
 fprintf(fid_9,format_100, xout(i),cp(i));
end;  i=50+1;
end %program joukow

They both give the same results for me. I didn't check the algorithm for correctness, though, just converted the code.

千と千尋 2024-10-07 15:13:11

我不知道它的支持程度如何 - 但最简单的方法是 f2c,它将 fortran 直接转换为 c 代码。

I don't know how well it's still supported - - but the easiest way used to be f2c which translates fortran directly into c code.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文