在fortran中传递指针参数
我想知道什么是编写下面的代码的正确方法?在fortran中传递指针参数
PROGRAM foo
INTEGER :: x
REAL(KIND=8), TARGET, DIMENSION(0: 10) :: array
REAL(KIND=8), POINTER, DIMENSION(:) :: ptr
ptr => array
CALL bar(ptr)
END PROGRAM foo
SUBROUTINE bar (ptr)
REAL(KIND=8), POINTER, DIMENSION(:) :: ptr
INTEGER x
DO x =0, 10
ptr(x) = 2 // seg faults
ENDDO
END SUBROUTINE bar
它的工作原理,如果我在bar
声明ptr
为REAL(KIND=8), DIMENSION(0:10)
。但总的来说,我可能不知道传入数组的大小,那么有没有办法将ptr
声明为某个数组的指针?我正在编译gfortran
如果一个过程有一个伪参数是一个指针,那么在任何调用范围内都需要一个显式接口。
(有需要显式接口许多事情,指针假,只有一个。)
您可以通过将接口块为您的子程序主程序里面自己提供显式接口。另一种远远更好的选择是将子程序放入模块中,然后在主程序中使用该模块。第三种方法是使子程序成为调用范围的内部过程。
从Fortran 2003开始,如果您打算将指针指向不同的东西,则应该只使用指针。如果你只是使用指针来表示真正的行为就像一个值,那么你应该使用allocatables。
这取决于你的意思是“正确”的方式。作为IanH已经pointed out,你需要一个明确的接口(最好通过在模块中包装东西完成),如果可能的话,使用可分配的而不是指针。
我还想补充一点,如果你不想在你的子程序中改变你的数组的分配状态,但只想操纵它的元素,那么在你的子程序中使用一个简单的假定形状数组。下面你会找到一个工作的例子。一些事情需要注意:
不要使用
real(kind=8)
,因为不是所有的编译器使用的字节数作为一种为实数。如果你想要双精度精度,请明确要求如下。如果你只是想填补一个恒定值的数组,这样做的简单的方法:
array(:) = 2.0_dp
而且这里的例子:
module accuracy
implicit none
integer, parameter :: dp = kind(1.0d0)
end module accuracy
module barmodule
use accuracy
implicit none
contains
subroutine bar(array)
real(dp), intent(inout) :: array(:)
integer :: ii
do ii = 1, size(array)
array(ii) = ii
end do
end subroutine bar
end module barmodule
program foo
use accuracy
use barmodule
implicit none
real(dp), dimension(0:10) :: array
call bar(array)
end program foo
如果您希望数组为零索引,您可以在子例程中声明它为'array(0:)'。它允许假定形状,但指定起始索引。这可以被概括,直到将起始索引作为参数传递。 – 2014-08-31 08:41:01
你是对的!谢谢!这是我已经打了很多次的东西......我已经从帖子中删除了appropraite部分。 – 2014-08-31 09:08:09
这是一个情况下的'foo'中'bar'需要_explicit interface_。例如,参见http://*.com/q/9374691/3157076。 – francescalus 2014-08-31 00:59:57
看来你试图复制C,最好是在Fortran中思考。仔细阅读Bálint的回答,虽然伊恩也是对的。 – 2014-08-31 09:15:31