How to declare the type of a function that returns an array in Fortran?

こ雲淡風輕ζ 提交于 2021-02-04 07:26:07

问题


I have function that returns an array, say

function f(A)
    implicit none
    real, intent(in) :: A(5)
    real, intent(out) :: f(5)

    f = A+1
end

My question is, how can I define f in the main program unit? E.g.

program main
    implicit none
    real :: A(5)
    real, dimension(5), external :: f  ! does not work

    ...
end 

回答1:


You need an explicit interface. You can do this in a few ways.

  1. Explicitly in the scoping unit that calls f:

    interface
      function f(A)
        implicit none
        real, intent(in) :: A(5)
        real :: f(5)
      end function
    end interface
    
  2. Place the function in your program host scope as an internal function:

     program main
        ...
     contains
       function f(A)
         implicit none
         real, intent(in) :: A(5)
         real :: f(5)
    
         f = A+1
       end
     end program
    
  3. Place the function in a module:

     module A
     contains
       function f(A)
         implicit none
         real, intent(in) :: A(5)
         real :: f(5)
    
         f = A+1
       end
     end module
    
     program main
       use A
       ...
     end program
    
  4. Use the explicit interface from a different procedure with the same arguments and return type, kind and rank.

    program main
      interface
        function r5i_r5o(r5)
          implicit none
          real, intent(in) :: r5(5)
          real :: r5i_r5o(5)
        end function
      end interface
    
      procedure(r5i_r5o) :: f
      ...
    end program
    
    function f(A)
      implicit none
      real, intent(in) :: A(5)
      real :: f(5)
    
      f = A+1
    end
    

The cleanest way of doing this is option #3 using modules. This gives you the benefit of an automatic explicit interface (not needing to do option #1 everywhere you call f) and makes your function available everywhere the module is used rather than limited to a specific scoping unit as in option #2. Option #4 can be handy if you have many procedures with the same argument and return types since one explicit interface can be re-used for all of them.




回答2:


This shows three different ways to specify function results, and how to use modules to organize your functions:

module so_func

    INTEGER, PARAMETER :: MAX_SIZE = 5

    TYPE MY_DATA
        INTEGER :: SIZE
        REAL, DIMENSION(MAX_SIZE) :: DATA
    ENDTYPE


contains

    FUNCTION f1(A,N) RESULT(X)
    implicit none
    INTEGER, INTENT(IN) :: N
    REAL, INTENT(IN) :: A(N)
    REAL :: X(N)
    ! ....
    X = 1.0+A
    END FUNCTION f1

    TYPE(MY_DATA) FUNCTION f2(A,N)
    implicit none
    INTEGER, INTENT(IN) :: N
    REAL, INTENT(IN) :: A(N)
    ! ....
    f2%SIZE = N
    f2%DATA(1:N) = 1.0+A
    END FUNCTION f2

    FUNCTION f3(A,N)
    implicit none
    INTEGER, INTENT(IN) :: N
    REAL, INTENT(IN) :: A(N)
    REAL :: f3(N)
    ! ....
    f3 = 1.0+A
    END FUNCTION f3

end module


program SO_RESULT
    use so_func
    implicit none
    integer, parameter :: n=5
    REAL :: A(n), y1(n), y3(n)    
    TYPE(MY_DATA) :: y2
    INTEGER :: i
    ! Variables

    A =(/ (i, i=1,n) /)

    y1 = f1(A,n)
    y2 = f2(A,n)
    y3 = f3(A,n)


end program SO_RESULT


来源:https://stackoverflow.com/questions/26347090/how-to-declare-the-type-of-a-function-that-returns-an-array-in-fortran

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!