Decimal Literal decimal floating-point numbers cannot always be precisely represented as a BigDecimal
when the BigDecimal(double val)
constructor is used. The primitive type double
cannot precisely represent all decimal fractions because its underlying representation is binary. Consequently, the input to the an IEEE 754 floating-point value. Consequently, the BigDecimal(double val)
constructor can lose precision before the constructor is ever invokedmust not be passed a floating-point literal as an argument when doing so results in an unacceptable loss of precision.
Noncompliant Code Example
This noncompliant code example passes a double
value to the BigDecimal
constructor. Because of thisthe decimal literal 0.1
cannot be precisely represented by a double
, precision of the literal BigDecimal
is affected.
Code Block | ||
---|---|---|
| ||
// printsPrints 0.1000000000000000055511151231257827021181583404541015625 // when run in FP-strict mode System.out.println(new BigDecimal(0.1)); |
Compliant Solution
This compliant solution passes the decimal literal as a String
so that the BigDecimal(String val)
constructor is invoked . and the precision is preserved:
Code Block | ||
---|---|---|
| ||
// printsPrints 0.1 // when run in FP-strict mode System.out.println(new BigDecimal("0.1")); |
Risk Assessment
Using the BigDecimal(double val)
constructor with decimal floating-point literals leads can lead to loss of precision.
Rule | Severity | Likelihood | Remediation Cost | Priority | Level |
---|
NUM10-J |
Low |
Probable |
Low | P6 | L2 |
Automated Detection
Automated detection appears to be is straightforward.
Related Vulnerabilities
Search for vulnerabilities resulting from the violation of this guideline on the CERT website.
Bibliography
[JLS 2005]
...
Tool | Version | Checker | Description | ||||||
---|---|---|---|---|---|---|---|---|---|
Parasoft Jtest |
| CERT.NUM10.BBDCC | Do not pass floating point values to the 'BigDecimal' constructor | ||||||
PVS-Studio |
| V6068 | |||||||
SonarQube |
| S2111 | "BigDecimal(double)" should not be used |
Bibliography
...
use floating point variables as loop counters Floating Point (FLP) FLP09-J. Do not rely on the default string representation of floating point values