Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

Using integer arithmetic to calculate a value for assignment to a floating-point variable may lead to loss of information. This can be avoided by converting one of the integers in the expression to a floating type.

When converting integers to floating-point values, and vice versa, it is important to carry out proper range checks to avoid undefined behavior (see FLP34-C. Ensure that floating point conversions are within range of the new type).

It may be desirable to have the operation take place as integers before the conversion (obviating the need for a trunc() call, for example). If that is done, it should be clearly documented to help future maintainers understand the intent of the code.

Noncompliant Code Example

In this noncompliant code , the floating point example the division and multiplication operations take place on integers and then get converted to floating point. This causes floating-point variables d, e, and f are to not be initialized correctly because the operations take place before the values are converted to floating-point values and hence the . The results are truncated to the nearest integer or may overflow. Consequently, the division and multiplication operations take place on integers and then get converted to floating point.

Code Block
bgColor#FFCCCC
short a = 533;
int b = 6789;
long c = 466438237;

float d = a / 7; /* d is 76.0 */
double e = b / 30; /* e is 226.0 */
double f = c * 789; /*  f may be negative due to overflow */

Compliant Solution

...

(Floating Point Literal)

In this compliant solution, the decimal error in initialization is eliminated by ensuring that at least one of the operands to the division operation is floating point.

...

Compliant Solution 2

In this compliant codesolution, the decimal error in initialization is eliminated by first storing the integer in the floating-point variable and then performing the arithmetic operation. This ensures that at least one of the operands is a floating-point number, and consequently the operation is performed on floating point numbers.

Code Block
bgColor#CCCCFF
short a = 533;
int b = 6789;
long c = 466438237;

float d = a;
double e = b;
double f = c;

d /= 7; /* d is 76.14286 */
e /= 30; /* e is 226.3 */
f *= 789; /* f is 368019768993.0 */

Exceptions

FLP33-EX1: It may be desirable to have the operation take place as integers before the conversion (obviating the need for a call to trunc(), for example). If this is the programmer's intention, it should be clearly documented to help future maintainers understand that this behavior is intentional.

Risk Assessment

Improper conversions between integers and floating point values may yield unexpected results, especially loss of precision. Additionally, these unexpected results may actually involve overflow, or undefined behavior.

...

Wiki Markup
\[[Hatton 95|AA. C References#Hatton 95]\] Section 2.7.3, "Floating-point misbehavior"
\[[ISO/IEC 9899:1999|AA. C References#ISO/IEC 9899-1999]\] Section 5.2.4.2.2, "Characteristics of floating types <{{float.h}}>"
\[[MITRE 07|AA. C References#MITRE 07]\] [CWE ID 681|http://cwe.mitre.org/data/definitions/681.html], "Incorrect Conversion between Numeric Types,"; and [CWE ID 682|http://cwe.mitre.org/data/definitions/682.html], "Incorrect Calculation"

...