Intel® Fortran Compiler
Build applications that can scale for the future with optimized code designed for Intel® Xeon® and compatible processors.

Why value of local array is saved between function calls?

S__MPay
Beginner
530 Views

I noticed if I define a local variable in a function:

realdimension(n1, n2) :: myArray

myArray will keep its last values next time I call function causing wrong calculations.
Before I assumed dimension keyword will allocate and initialize an array with zero members.
How can I prevent this and reset the array. I think using myArray(:, :) = 0. is not efficient.

0 Kudos
1 Solution
Andrew_Smith
New Contributor III
530 Views

Arrays and scalars are not initialized to zero by default. It is not standard Fortran to do so but you can set a compiler flag to make it happen.

Explicit setting to zero is better practice and will be efficiently done by the compiler, no less so than a zero setting to zero by compiler flag.

There is a useful compiler setting to set signalling nan to these floating point types and it would help you detect any more cases where you assumed zero.

View solution in original post

0 Kudos
6 Replies
Andrew_Smith
New Contributor III
531 Views

Arrays and scalars are not initialized to zero by default. It is not standard Fortran to do so but you can set a compiler flag to make it happen.

Explicit setting to zero is better practice and will be efficiently done by the compiler, no less so than a zero setting to zero by compiler flag.

There is a useful compiler setting to set signalling nan to these floating point types and it would help you detect any more cases where you assumed zero.

0 Kudos
Arjen_Markus
Honored Contributor I
530 Views

Note that instead of:

myArray(:,:) = 0

you can also use:

myArray = 0

 

 

0 Kudos
mecej4
Honored Contributor III
530 Views

A local variable, strictly speaking, is undefined whenever the subprogram is entered, unless it has the SAVE attribute. It is the programmer's responsibility to do any desired initialization.

There is no compiler option to zero a variable each time the subprogram is entered. You can request the zeroing to be done when the program starts. The variable will then be zero only when the subprogram is entered the first time. Even then, the values of unsaved local variables will be undefined for subsequent entries to the same subprogram. They may retain the values from the previous entry, by coincidence, or the values may be trash values that were placed in the same memory locations in another subprogram.

0 Kudos
TimP
Honored Contributor III
530 Views

Ifort gives local arrays a default SAVE attribute.  This is among the reasons for recommending decorating procedures which should be thread safe with RECURSIVE.  Compile flag -Qauto and others which imply it have the same effect.

As mentioned above, if you want the array zeroed each time you should assign 0 explicitly.  Ifort normally would generate efficient code for this, likely with a memset function call.

0 Kudos
Steve_Lionel
Honored Contributor III
530 Views

Some additional comments...

- /Qauto or similar will replace the "remembered values" with random values from whatever was on the stack. The arrays will not be reset to zero.

- The compiler option to zero-initialize variables happens before the program starts - it does not reset values on each procedure call.

Explicit code to zero-initialize the arrays is the only correct way of solving this issue.

0 Kudos
S__MPay
Beginner
530 Views

Here I will post a summary of all the answers:

Andrew Smith wrote:

Arrays and scalars are not initialized to zero by default. It is not standard Fortran to do so[...]

Explicit setting to zero is better practice and will be efficiently done by the compiler [...]

mecej4 wrote:

There is no compiler option to zero a variable each time the subprogram is entered. [...]

Steve Lionel (Ret.) wrote:

[...]

- /Qauto or similar will replace the "remembered values" with random values from whatever was on the stack. The arrays will not be reset to zero.

- The compiler option to zero-initialize variables happens before the program starts - it does not reset values on each procedure call.

Explicit code to zero-initialize the arrays is the only correct way of solving this issue.

Arjen Markus wrote:

Note that instead of:

myArray(:,:) = 0

you can also use:

myArray = 0

0 Kudos
Reply