1. 程式人生 > >java之BigDecimal的加減乘除

java之BigDecimal的加減乘除

在小數之間加減乘除的時候,由於二進位制不能精確表示小數,從而導致精度丟失。在實際開發中,這種情況是很糟糕的。為了解決這一情況,我們可以利用BgiDecimal。但是這中間還有些問題需要注意的。
1、加減乘 首先,我們來看一個例項
BigDecimal num1 = new BigDecimal(3.0);
BigDecimal num2 = new BigDecimal(2.1);
System.out.println(num1.add(num2));
列印結果
並不是我們期望的結果,從jdk參考手冊,我們可以找到原因
  1. The results of this constructor can be somewhat unpredictable. One might assume that writingnew BigDecimal(0.1)
    in Java creates aBigDecimal which is exactly equal to 0.1 (an unscaled value of 1, with a scale of 1), but it is actually equal to 0.1000000000000000055511151231257827021181583404541015625. This is because 0.1 cannot be represented exactly as adouble (or, for that matter, as a binary fraction of any finite length). Thus, the value that is being passedin
    to the constructor is not exactly equal to 0.1, appearances notwithstanding.
  2. The String constructor, on the other hand, is perfectly predictable: writingnew BigDecimal("0.1") creates aBigDecimal which is exactly equal to 0.1, as one would expect. Therefore, it is generally recommended that theString
    constructor
    be used in preference to this one.
  3. When a double must be used as a source for a BigDecimal, note that this constructor provides an exact conversion; it does not give the same result as converting thedouble to aString using the Double.toString(double) method and then using theBigDecimal(String) constructor. To get that result, use thestatic valueOf(double) method. 

我們再來看另外一個例子
BigDecimal num1 = BigDecimal.valueOf(3.0);
BigDecimal num2 = BigDecimal.valueOf(2.1);
System.out.println(num1.add(num2));

列印輸出
這次是我們期望的結果。 所以,我建立BigDecimal物件的時候,最好通過靜態方法valueOf(double)
當然,我們也可以通過另外一種方式。先將double值轉為字串,再通過Bigdecimal的建構函式建立物件
BigDecimal num1 = new BigDecimal(Double.toString(3.0));//或者3.0 + ""
BigDecimal num2 = new BigDecimal(Double.toString(2.1));//或者2.1 + ""
System.out.println("add->"+num1.add(num2));
System.out.println("subtract->"+num1.subtract(num2));
System.out.println("multiply->"+num1.multiply(num2));
列印輸出
2.除 jdk提供了幾種小數之間相除的方法。
BigDecimal num1 = new BigDecimal(3.0);
BigDecimal num2 = new BigDecimal(2.1);
System.out.println("divide->"+num1.divide(num2));
直接執行,奇怪的發現出現異常了
從異常資訊可以知道,相除的結果不能夠用二進位制精確表示,所以需要使用另外一個方法
BigDecimal num1 = new BigDecimal(3.0); BigDecimal num2 = new BigDecimal(2.1); System.out.println("divide->"+ num1.divide(num2,3,RoundingMode.FLOOR));
第二個引數表示,當結果是無限小數時,保留幾位有效數字 第三個引數表示,如何保留有效數字,例如四捨五入、向下取等

<script>
var _hmt = _hmt || [];
(function() {
  var hm = document.createElement("script");
  hm.src = "https://hm.baidu.com/hm.js?5e96c091ce7bc89fd43194bbc14eaadc";
  var s = document.getElementsByTagName("script")[0]; 
  s.parentNode.insertBefore(hm, s);
})();
</script>