因爲須要計算金額,全部須要高精度計算,全部須要使用 BigDecimal 類。
BigDecimal可以精確的表示一個小數,經常使用於商業和科學計算;float,double不能精確的表示一個小數。java
分別用兩種不一樣的數據類型(long 和 string)建立 BigDecimal 對象;ide
import java.math.BigDecimal; public class BigDecimalTest { /** * 使用BigDecimal,參數類型是double類型,計算仍是不精確 */ @Test public void testAdd1(){ BigDecimal b1 = new BigDecimal(0.05); BigDecimal b2 = new BigDecimal(0.01); System.out.println(b1.add(b2)); //輸出:0.06000000000000000298372437868010820238851010799407958984375 } /** * 使用BigDecimal,參數類型是String類型,計算結果精確 */ @Test public void testAdd2(){ BigDecimal b1 = new BigDecimal("0.05"); BigDecimal b2 = new BigDecimal("0.01"); System.out.println(b1.add(b2)); //輸出:0.06 } }
從上面的結果能夠看出使用 string 類型的才能獲得精確的計算結果。全部在計算金額時注意使用 string 類型建立對象。函數
import java.math.BigDecimal; public class BigDecimalTest { /** * 測試減法 參數類型是double類型,計算仍是不精確 */ @Test public void testSubtract1(){ BigDecimal b1 = new BigDecimal(0.05); BigDecimal b2 = new BigDecimal(0.01); System.out.println(b1.subtract(b2)); //輸出:0.04000000000000000256739074444567449972964823246002197265625 } /** * 測試減法,參數類型是String類型,計算結果精確 */ @Test public void testSubtract2(){ BigDecimal b1 = new BigDecimal("0.05"); BigDecimal b2 = new BigDecimal("0.01"); System.out.println(b1.subtract(b2)); //輸出:0.04 } }
import java.math.BigDecimal; public class BigDecimalTest { /** * 測試乘法 參數類型是double類型,計算仍是不精確 */ @Test public void testMultiply1(){ BigDecimal b1 = new BigDecimal(0.05); BigDecimal b2 = new BigDecimal(0.01); System.out.println(b1.multiply(b2)); //輸出:0.0005000000000000000381639164714897566548413219067927041589808827754781955614304944646164585719816386699676513671875 } /** * 測試乘法,參數類型是String類型,計算結果精確 */ @Test public void testMultiply2(){ BigDecimal b1 = new BigDecimal("0.05"); BigDecimal b2 = new BigDecimal("0.01"); System.out.println(b1.multiply(b2)); //輸出:0.0005 } }
因爲10/3除不盡,商是無限小數,因此報錯;
Non-terminating decimal expansion; no exact representable decimal result.測試
import java.math.BigDecimal; public class BigDecimalTest { /** * 測試除法 參數類型是double類型 */ @Test public void testDivide1(){ BigDecimal b1 = new BigDecimal(0.1); BigDecimal b2 = new BigDecimal(0.03); System.out.println(b1.divide(b2)); //報錯 java.lang.ArithmeticException: Non-terminating decimal expansion; no exact representable decimal result. } /** * 測試除法,參數類型是String類型 */ @Test public void testDivide2(){ BigDecimal b1 = new BigDecimal("0.1"); BigDecimal b2 = new BigDecimal("0.03"); System.out.println(b1.divide(b2)); //報錯 java.lang.ArithmeticException: Non-terminating decimal expansion; no exact representable decimal result. } }
其實devide的函數定義以下:
BigDecimal.divide(BigDecimal divisor, int scale, RoundingMode roundingMode);code
小數模型有如下類型:對象
全部除法應該寫成如下形式;
BigDecimal num3 = num1.divide(num2,10,ROUND_HALF_DOWN);ip
import java.math.BigDecimal; public class BigDecimalTest { /** * 測試除法 參數類型是double類型 */ @Test public void testDivide3(){ BigDecimal b1 = new BigDecimal(0.1); BigDecimal b2 = new BigDecimal(0.03); System.out.println(b1.divide(b2, 10, ROUND_HALF_DOWN)); //輸出:3.3333333333 } /** * 測試除法,參數類型是String類型 */ @Test public void testDivide4(){ BigDecimal b1 = new BigDecimal("0.1"); BigDecimal b2 = new BigDecimal("0.03"); System.out.println(b1.divide(b2, 10, ROUND_HALF_DOWN)); //輸出:3.3333333333 }