链接:https://juejin.im/post/5e86085ce51d4547153d0769
前言
通常商业计算涉及到小数的,我们都会使用 BigDecimal 来完成加减乘除运算。但是利用 BigDecimal 进行浮点数精确运算时,需要注意使用正确的方法。如果方法选择不当,依旧会发生错误。
发现问题
1public class Test {
2 public static void main(String[] args) {
3 BigDecimal multiply = BigDecimal.valueOf(9.9f).multiply(BigDecimal.valueOf(100f)); 4 System.out.println(multiply.toString()); 5 6 BigDecimal multiply2 = new BigDecimal(Float.toString(9.9f)).multiply(BigDecimal.valueOf(100f)); 7 System.out.println(multiply2.toString()); 8 } 9}1011//result12989.999961853027300013990.00
测试 BigDecimal 的两种构造方法,发现浮点运算的结果不同。利用 BigDecimal.valueOf 方法构造对象的方法,获得的浮点数发生了精度异常。利用 new BigDecimal(String val) 方法,运算正确。
分析原因
查看 BigDecimal.valueOf 源码,我们可以发现问题。BigDecimal.valueOf(9.9f) 实际调用的方法是 java.math.BigDecimal#valueOf(double)。如下图所示:
1 /** 2 * Translates a {