Loss of Precision

Where does Loss of Precision Occur?

There are two contexts where loss of precision may be identified.

• Where the result of an expression has a higher precision than that of variables within the expression. The high precision result may then contain a low precision value.
• A special case is identified where a high precision result is generated from an expression containing low precision literal numbers.

Do All of These Mixed Precision Expressions Cause Problems?

No. Some low precision real values have exact representations with the same value in high and low precision. Also, it is common practice in simulation programs to compute derivatives at low precision and then to compute the integrals at high precision. The integration routines therefore contain mixed precision expressions.

Checking for Loss of Precision

The fpt command CHECK EXPRESSIONS traps all cases of mixed precision within expressions or across an equals sign. For example, in the "Earth Systems Modeling Framework" used in the climate and weather modelling code WRF, we check expressions, and then search interactively for the errors marked in the code by fpt. We find the current scope and then examine the variable dt and the function real_time. The 8-byte real variable dt will contain a value with only 4-byte precision.

168 ! 169 ! ! 170 ! ! Here, we round off dtInterval to nearest 1/100. This prevents 171 ! ! the denominator from getting too large and causing overflow. 172 ! ! 173 >> dt = real_time(dtinterval) !---------------------------------^------------------------------------ !!! FPT - 3069 The left-hand-side variable will not have the expected p !---------------------------------------------------------------------- 174 num = NINT(dt*precision) 175 den = precision 176 CALL wrfu_timeintervalset(dtinterval,SN = num,SD = den) 177 ! 178 ! ! Limit the maximum dtInterval based on user input 179 ! 180 IF (grid%max_time_step_den .EQ. 0) THEN FPT> show cursor The cursor is at line: 173 in file: .../UCAR_clean_build_WRFV3.6.1/WRFV3/dyn_em/adapt_timestep_em.F At line: 173 in sub-program: adapt_timestep Current scope is "ALL FILES" FPT> show symbol adapt_timestep%dt Name Scope Use/COMMON Address Type Size Value/Bounds ---- ----- ---------- ------- ---- ---- ------------ dt adapt_timestep Local DOUBLE PRECISION *8 df 1 matching symbol FPT> show symbol real_time Name Scope Use/COMMON Address Type Size Value/Bounds ---- ----- ---------- ------- ---- ---- ------------ real_time Global Function REAL *4 df 1 matching symbol FPT>

Correcting the Precision of Literal Real Numbers

The fpr command:

changes the text of literal numbers in the code wherever they are used in a context where a higher precision would be appropriate. fpt changes the exponent character from "E" to "D" or adds the exponent "D0" if no exponent is specified. No change is made if the number already has a kind tag.

When a literal number is changed, fpt compares the high and low precision values of the number, and reports the situation where the new value differs from the old value. At the end of the correction pass fpt makes a summary report of the numbers tested and changed. The end of the report for WRF is shown below:

------------------------------------------------------------------------------ NOTE Number 3743 Severity 0 (Worst 2) Count 33076 Line 1714 File: ...publication/test/UCAR_clean_build_WRFV3.6.1/WRFV3/share/module_llxy.F col = col+0.0002D0 ^ Real literal precision increased with a small change in value ------------------------------------------------------------------------------ ------------------------------------------------------------------------------ NOTE Number 3743 Severity 0 (Worst 2) Count 33077 Line 1955 File: ...publication/test/UCAR_clean_build_WRFV3.6.1/WRFV3/share/module_llxy.F REAL(KIND = high),PARAMETER :: pi = 3.141592653589793D0 ^ Real literal precision increased with a small change in value ------------------------------------------------------------------------------ ------------------------------------------------------------------------------ NOTE Number 3743 Severity 0 (Worst 2) Count 33078 Line 1990 File: ...publication/test/UCAR_clean_build_WRFV3.6.1/WRFV3/share/module_llxy.F REAL(KIND = high),PARAMETER :: pi = 3.141592653589793D0 ^ Real literal precision increased with a small change in value ------------------------------------------------------------------------------ Promotion of Literal REAL Numbers ================================= Count Percent REAL literal numbers: 157120 With KIND tags: 19327 12.30% Promoted to higher precision: 26809 17.06% Promoted with change in value: 23034 14.66% Not promoted: 110956 70.62%