![](/img/trans.png)
[英]IBM java8 BigDecimal floating issue with MathContext.DECIMAL64
[英]BigDecimal - MathContext.DECIMAL64 vs MathContext.DECIMAL128
我正在处理货币价值之间的分歧。 我目前正在使用MathContext.DECIMAL128
作为BigDecimal.divide()
第二个参数。 我应该使用MathContext.DECIMAL128
还是MathContext.DECIMAL64
吗?
十进制32,十进制64和十进制128之间的区别是(来自https://bloomberg.github.io/comdb2/decimals.html ):
decimal32支持-95到+96之间的指数; 有效数字有7位数字(即0.000000-9.999999)。
此格式可表示的数字范围是+ -0.000000x10-95至+ -9.999999x10 + 96
decimal64支持-383至+384之间的指数; 有效数字有16个数字(即0.000000000000000-9.999999999999999)。 数字范围是+ -0.000000000000000x10−383到+ -9.999999999999999x10 + 384
decimal128支持-6143和+6144之间的指数; 有效数字有34个数字(即0.000000000000000000000000000000000-9.999999999999999999999999999999999)。
数字范围是+ -0.000000000000000000000000000000000x10−6143至+ -9.999999999999999999999999999999999x10 + 6144
我们可以发现差异是范围。
BigDecimal支持一种特殊的舍入模式:UNLIMITED,但是如果我们使用UNLIMITED,则无限循环十进制结果将引发ArithmeticException。
例:
public static void main(String[] args) {
BigDecimal bd = new BigDecimal(1);
BigDecimal bd2 = new BigDecimal(3);
BigDecimal result = bd.divide(bd2, MathContext.DECIMAL32);
System.out.println(result);
result = bd.divide(bd2, MathContext.DECIMAL64);
System.out.println(result);
result = bd.divide(bd2, MathContext.DECIMAL128);
System.out.println(result);
result = bd.divide(bd2, MathContext.UNLIMITED);
System.out.println(result);
}
输出:
0.3333333
0.3333333333333333
0.3333333333333333333333333333333333
Exception in thread "main" java.lang.ArithmeticException: Non-terminating decimal expansion; no exact representable decimal result.
因此,如果想要更大的结果范围,则应使用decimal128或UNLIMITED(但要注意无限循环十进制,它将抛出ArithmeticException),否则,应使用decimal64或decimal32,因为范围较大意味着性能较差。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.