本文介绍了模块调用具有隐式接口的外部过程的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

以下代码,结合了模块程序外部程序:

module module_dummy

  implicit none

contains

  subroutine foo(a)

    real, intent(inout) :: a(:)

    call bar(a)

  end subroutine foo

end module module_dummy

program main

  use module_dummy

  implicit none

  integer, parameter :: nelems = 100000000
  real,  allocatable :: a(:)

  allocate( a(nelems) )
  a = 0.0
  call foo(a)
  print *, a(1:10)
  deallocate(a)

end program main

subroutine bar(a)

  implicit none

  real, intent(inout) :: a(:)

  a = 1.0

end subroutine bar

似乎都失败了:

  1. 分段错误
  2. 打印一块 0.000 而不是 1.000

在我迄今为止尝试过的任何平台上.该问题与bar隐式接口声明有关,实际上该问题可以通过任何方式添加显式接口来解决,例如使用:

on any platform I have tried so far. The problem is related to the implicit interface declaration of bar, and in fact the issue can be solved adding in any way an explicit interface, e.g. using:

module module_dummy

  implicit none

contains

  subroutine foo(a)

    interface
       subroutine bar(x)
         real, intent(inout) :: x(:)
       end subroutine bar
    end interface

    real, intent(inout) :: a(:)

    call bar(a)

  end subroutine foo

end module module_dummy

或在模块中声明 bar 以供 module_dummy 使用.

or declaring bar inside a module to be used by module_dummy.

无论如何,我一开始真的不明白错误是什么.我在 Fortran 90 标准(第 12.3.2.4) 说:

Anyhow I really don't understand what is the error in the first place. What I have found on the Fortran 90 standard (sec. 12.3.2.4) says that:

过程的伪参数的类型、类型参数和形状从范围单元引用,其中过程的接口是隐式必须是这样的,实际参数与虚拟参数的特征.

在这种情况下,规则似乎受到尊重,因为 a 总是声明为

In this case the rule seems to be respected, as a is always declared as

real, intent(inout) :: a(:)

那么,我在解释使之前代码出错的标准时遗漏了什么?

So, what am I missing in the interpretation of the standard that makes the previous code wrong?

推荐答案

假定形状的虚拟参数必须在其引用点具有显式接口.F90 12.3.1.1 第 2c 项.

Dummy arguments that are assumed shape must have an explicit interface at their point of reference. F90 12.3.1.1 item 2c.

实际上,假定的形状数组是通过传递一个描述符来传递的——一个描述数组的边界和存储位置的小结构.Ye-olde F77 显式形状和假定大小数组仅通过传递第一个元素的地址来传递.如果没有显式接口,编译器不知道它需要构建和传递描述符 - 因此会导致混乱和混乱.

Practically, assumed shape arrays are passed by passing a descriptor - a little structure that describes the bounds and the location of storage of the array. Ye-olde F77 explicit shape and assumed size arrays are passed simply by passing the address of the first element. Without the explicit interface the compiler doesn't know that it needs to build and pass the descriptor - hence chaos and confusion results.

这篇关于模块调用具有隐式接口的外部过程的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

07-30 01:42