fortran结果变量未初始化

时间:2013-10-13 00:39:38

标签: fortran fortran90

我遇到了关于loacal变量初始化的问题。

我有以下函数来计算gammar

function gammar(z) result(gz)
implicit none
real(8),intent(out)::gz
real(8)::z,t,low,up
real(8),parameter::increment=1.0
real(8),parameter::lower_t=0.0,upper_t=10.0
integer(4)::i,n
!gz=0.0
n=(upper_t-lower_t)/increment
do i=1,n
low=lower_t+(i-1)*increment
up=lower_t+(i)*increment
gz=gz+(f(z,low)+f(z,up))*increment/2.0
end do
end function gammar

Then I call this function in main program like
df=9.0
t=0.0
write(*,*) gammar((df+1.0)/2.0)/sqrt(pi*df)/gammar(df/2.0)

我得错了答案!! 0.126 我发现原因是在计算了gammar((df + 1.0)/2.0)之后,局部变量gz没有设置为0。 因此,当计算gammar(df / 2.0)时,gz仍保留旧值24.最终,gammar(df / 2.0)得到了错误答案34 .. 如果我在gammar函数中添加gz = 0.0,则此问题已得到修复。 这真的很令人惊讶。当gammar每次调用时,为什么本地gz没有初始化为零?

非常感谢

此致 柯

1 个答案:

答案 0 :(得分:1)

除非您有一个语句来初始化过程中的局部变量,例如您已注释掉的gz = 0,否则在调用过程时不会初始化这些局部变量。他们的价值观未定义。它们可以具有从先前调用中留下的值,或者某个随机值。

如果您使用编译器的完整警告选项,它可能会告诉您此问题。 gfortran在编译时警告过一个未初始化的变量。 ifort在运行时检测到问题。

另一种初始化方法是声明。这仍然不会重复该过程的其他调用的初始化。如果在具有声明的过程中初始化局部变量(例如integer :: count = 0),则仅在过程的第一次调用时执行初始化。但是......变量仍然被定义,并且在下一次调用时将保留它在前一次调用退出时所具有的值。

P.S。 real(8)不是获取双精度实数的可移植方法。语言标准没有为种类指定特定的数值...编译器可以随意使用任何值。大多数编译器使用字节数,但使用其他编号方法。最好使用selected_real_kindISO_FORTRAN_ENV和(对于双精度)real64。见quad precision in gfortran

P.P.S。使用gfortran尝试此代码,该编译器指出了gz的另一个问题:

function gammar(z) result(gz)
                             1
Error: Symbol at (1) is not a DUMMY variable

请删除声明中的intent(out)