BigDecimal
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了BigDecimal相关的知识,希望对你有一定的参考价值。
float和double类型的主要为了科学计算和工程计算而设计的,它们执行二进制浮点运算,这时为了在广泛的数值范围上提供较为精确的近似计算而精心设计的。然而,它们没有提供完全精确的结果,所以不应该被用于要求精确结果的场合。通常商业计算往往需要BigDecimal来计算精确要求比较高的数值。比如
public static void main(String[] args) { System.out.println(0.07 + 0.02); System.out.println(0.58 - 0.42); System.out.println(1.005 * 100); System.out.println(15.1 / 1000); }
输出的结果为:
0.09000000000000001
0.15999999999999998
100.49999999999999
0.015099999999999999
无论是在任何环境下,都需要将代码转为二进制机器码才能让机器识别,当浮点数直接输出时,会保持精度,而当浮点数进行计算后,可能会丢失精度,这时就需要BigDecimal来进行计算。
1.创建BigDecimal
BigDecimal中有一个以双精度浮点数为参数的构造函数,实际上传入浮点数进行计算时还是会精度丢失。
public static void main(String[] args) { BigDecimal num1 = new BigDecimal(1.005); BigDecimal num2 = new BigDecimal(100); BigDecimal num3 = new BigDecimal("1.005"); BigDecimal num4 = new BigDecimal("100"); System.out.println(num1.multiply(num2)); System.out.println(num3.multiply(num4)); }
输出分别为: 100.49999999999998934185896359849721193313598632812500 100.500
但是可以发现传入字符串时得到了精确的结果,还有BigDecimal.valueOf(double val)也可以得到精确地结果,可以看下面BigDecimal.valueOf(double val)的源码
public static BigDecimal valueOf(double val) { // Reminder: a zero double returns ‘0.0‘, so we cannot fastpath // to use the constant ZERO. This might be important enough to // justify a factory approach, a cache, or a few private // constants, later. return new BigDecimal(Double.toString(val)); }
此方法先是将参数转为了String类型,然后再调用参数为String类型的构造参数,所以在用BigDecimal时,尽量用new BigDecimal(String val) 或 BigDecimal.valueof(double val)来保证得到精确的结果。
2.compareTo
BigDecimal比较大小用compareTo()。
public static void main(String[] args) { System.out.println(BigDecimal.valueOf(0.05).compareTo(BigDecimal.valueOf(0.04))); System.out.println(BigDecimal.valueOf(0.04).compareTo(BigDecimal.valueOf(0.04))); System.out.println(BigDecimal.valueOf(0.03).compareTo(BigDecimal.valueOf(0.04))); }
输出为:
1
0
-1
BigDecimal.compareTo(BigDecimal val)
当BigDecimal比val大时返回1,
当BigDecimal小于val时返回-1,
当BigDecimal等于val时返回0。
以上是关于BigDecimal的主要内容,如果未能解决你的问题,请参考以下文章
如何在java代码中使用elasticsearch painless BigDecimal?