oop - 接受不同类型的 Fortran 函数

标签 oop fortran

我有三个转换角度的转换函数,代码如下所示。

函数返回的类型与输入的类型相同。这意味着 输入角度必须是程序员希望输出的类型 例如,将其转换为所需的输出类型 al = 转换(Real(30),"deg_to_rad")

我希望程序员能够执行al = Convert(30,"deg_to_rad")。 我有想法使用 transfer 内在的策略来定义 输出类型。

Real :: al, mold    
al = convert(30,"deg_to_rad", mold)
al = convert(30.0,"deg_to_rad", mold)

Double Precision :: al, mold    
al = convert(30,"deg_to_rad", mold)
al = convert(30.0,"deg_to_rad", mold)

这是我有的功能。有一些想法会很好 关于继续和实现良好计划的方法。

Interface convert
  Module Procedure convert
  Module Procedure convert_real
  Module Procedure convert_dble
  Module Procedure convert_real128
End Interface convert

Contains

Function convert_real   &
  (                &
    qa, label      &
  )                &
 Result (qb)

Real, Intent (in) :: qa
Character (len=*), Intent (in) :: label

Real :: qb

If (label .contains. "angle:") Then

 Block

   Real :: pi, deg_to_rad

   pi = 22.0 / 7.0
   deg_to_rad  = pi  / 180.0

   Select Case (Trim (label))

     Case ("angle: deg_to_rad")
       qb = deg_to_rad * qa

   End Select

 End Block

End If

End Function convert_real


Function convert_dble  &
  (                    &
    qa, label          &
  )                    &
 Result (qb)

Double Precision, Intent (in) :: qa
Character (len=*), Intent (in) :: label

Double Precision :: qb


If (label .contains. "angle:") Then

 Block

   Double Precision :: pi, deg_to_rad

   pi = Dble(22) / Dble(7)
   deg_to_rad  = pi / Dble(180)

   Select Case (Trim (label))

     Case ("angle: deg_to_rad")
       qb = deg_to_rad * qa

   End Select

 End Block

End If

End Function convert_dble


Function convert_real128  &
  (                       &
    qa, label             &
  )                       &
 Result (qb)

Real (Real128), Intent (in) :: qa
Character (len=*), Intent (in) :: label

Real (Real128) :: qb

If (label .contains. "angle:") Then

 Block

   Real (Real128) :: pi, deg_to_rad
   pi = Real(22,Real128) / Real(7,Real128)
   deg_to_rad  = pi / Real(180,Real128)

   Select Case (Trim (label))

     Case ("angle: deg_to_rad")
       qb = deg_to_rad * qa

   End Select

 End Block

End If

End Function convert_real128

当输入和输出不同时,我尝试使用子例程 类型。但是我收到以下错误

Subroutine convertor  & 
  (                   &
    qa, label, qb     &
  )

Class (*), Intent (in) :: qa
Character (len=*), Intent (in) :: label

Class (*), Intent (out) :: qb

Select Type (qb)

 Type Is (Real)
   qb = convert (Real(qa),label)

 Type Is (Double Precision)
   qb = convert (Dble(qa),label)

 Type Is (Real (Real128))
   qb = convert (Real(qa,Real128),label)

End Select

End Subroutine convertor

这是错误

gfortran -o build/lib/foul.o -c -ffree-form -g -J./build/lib lib/foul.f
gfortran -o build/lib/meidum.o -c -ffree-form -g -J./build/lib lib/meidum.f
lib/meidum.f:890.26:

   qb = convert (Real(qa),label)
                      1
Error: 'a' argument of 'real' intrinsic at (1) must be a numeric type
lib/meidum.f:893.26:

   qb = convert (Dble(qa),label)
                      1
Error: 'a' argument of 'dble' intrinsic at (1) must be a numeric type
lib/meidum.f:896.26:

   qb = convert (Real(qa,Real128),label)
                      1
Error: 'a' argument of 'real' intrinsic at (1) must be a numeric type

最佳答案

如果我理解你想要做什么,这似乎不必要地复杂。不要使用 transfer 作为模型,而是使用算术内部函数,例如 sin。 Fortran(自 FORTRAN 77 起)可以根据参数自动区分各种正弦函数(实数、 double 、四精度)。编写每个函数,然后编写一个接口(interface),将它们列为模块过程,以使它们通用。示例:Overloading functions with Fortran

编辑: 这取决于您想要什么:

result = convert (input)

对我来说,让函数返回的类型由参数input的类型控制似乎是最自然的。这就是我所描述的内容,也是示例中所示的内容。如果 结果 的类型不同,Fortran 将在赋值中进行转换...缺点是如果您选择了编译器选项,则会生成警告。因此,如果您希望 result 的类型控制 convert 计算的类型,则必须修改此技术。您不能使用函数,因为函数返回不区分此重载。请改用子例程,该子例程将有一个参数来区分:

call convert (input, result)

这在接口(interface)/模块过程中可以很好地工作。我不知道为什么认为这行不通。它在使用上可能比赋值语句/函数表示法不太优雅。

关于oop - 接受不同类型的 Fortran 函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27215204/

相关文章:

php - 如何在登录查询中检查哈希和盐?

c# - 重构具有不同属性的相同循环

C++:无法为 Vertex 对象创建哈希函数

fortran - MPI_Allgather 接收垃圾

对象创建时未创建 Python 新列表

php - 什么时候以及为什么我应该在 php 中使用类?

arrays - 一行中字符过多会导致 "Invalid form of array reference"错误?

fortran - 将派生类型的指针分配给 Fortran 中相同类型的目标

performance - 如何避免循环中的条件

c++ - Fortran 从 C 接受字符串(?)