NUM10-J. 浮動小数点数リテラルから BigDecimal クラスのオブジェクトを生成しない
10進数で表記された浮動小数点数リテラルは、IEEE 754浮動小数点数として、必ずしも正確に表現できるとは限らない。したがって、許容できない精度の欠損が発生するならば、コンストラクタBigDecimal(double val)の引数に浮動小数点数リテラルを渡してはならない。
違反コード
以下の違反コード例では、double型の値をBigDecimalクラスのコンストラクタに渡している。0.1という十進小数リテラルはdouble型として正確に表現することはできないため、構築されるBigDecimalオブジェクトの精度にも影響している。
// FP-strict モードで
// 0.1000000000000000055511151231257827021181583404541015625 を出力する
System.out.println(new BigDecimal(0.1));
適合コード
以下の適合コードでは、十進小数リテラルをStringとして渡しており、BigDecimal(String val)コンストラクタが呼び出され、精度が保たれる。
// FP-strict モードで
// 0.1 を出力する
System.out.println(new BigDecimal("0.1"));
リスク評価
BigDecimal(double val)コンストラクタを浮動小数点数リテラルを使って呼び出すと、精度の欠損を招く可能性がある。
|
ルール |
深刻度 |
可能性 |
自動検出 |
自動修正 |
優先度 |
レベル |
|---|---|---|---|---|---|---|
|
NUM10-J |
低 |
中 |
可 |
可 |
P6 |
L2 |
自動検出
自動検出は容易である。
| ツール | バージョン | チェッカー | 説明 |
|---|---|---|---|
| Klocwork |
2025.2 |
JAVA.BIGDEC.FLOAT |
|
| Parasoft Jtest | 2024.2 | CERT.NUM10.BBDCC | Do not pass floating point values to the 'BigDecimal' constructor |
| PVS-Studio |
7.38 |
V6068 |
|
| SonarQube | 9.9 | S2111 | "BigDecimal(double)" should not be used |
参考文献
|
[JLS 2015] |
|
| [Seacord 2015] |
翻訳元
これは以下のページを翻訳したものです。
NUM10-J. Do not construct BigDecimal objects from floating-point literals (revision 66)
