5

我有以下程序

module test
contains
   subroutine foo()
      integer, allocatable :: a(:)
      allocate(a(-5:5))
      call bar(a)
      print *, a
   end subroutine
   subroutine bar(a)
      integer, intent(out) :: a(:)
      a = 0 
      a(-4) = 3  ! here
      a(2) = 3   
   end subroutine
end module

program x
   use test
   call foo()
end program

在标有“这里”的行中,我做错了。事实是,当我收到数组a(在从 -5 到 +5 分配的调用者中)时,被调用者使用常规编号(1 到 n),这意味着分配 -4 我正在执行超出边界的分配。我如何指示编译器在bar例程中,a数组的编号必须与调用者中的编号相同?

4

3 回答 3

4

您在子例程中使用的虚拟参数类型(尺寸用冒号指定)称为“假定形状”。这个名字就是线索——Fortran 只传递形状而不传递上下限。除非您按照 kemiisto 的答案所示覆盖它,否则下限被假定为 1。如果下限不固定,您可以传递一个参数以用作下限。

稍后添加:如果在编译时不知道较低维度的代码示例:

subroutine example (low, array)
   integer, intent (in) :: low
   real, dimension (low:), intent (out) :: array
于 2010-12-06T15:27:02.443 回答
3

有两种常见的选择:

  • 正如kemisto 所写,您传递了第二个参数。这在 F77 风格的代码中很常见。你不能使用 LBOUND 技巧!它必须作为整数传递。
  • You declare the argument to be a pointer, which includes the entire array descriptor. Then the bounds of the array in the subroutine are the same as in the calling scope. Of course you may lose on optimization this way.
于 2010-12-07T10:44:15.133 回答
2

如何指示编译器在 bar 例程中,a 数组的编号必须与调用者中的编号相同?

不确定,但根据标准,您可以指定假定形状数组的下限。

subroutine bar(a)
      integer, intent(out) :: a(-5:)
于 2010-12-06T14:08:26.983 回答