解決double型別相減有誤差的問題

mlgglm發表於2015-09-06

今天在寫指令碼時發現double 型別的相減 跟實際結果有誤差,如 :19.9-9.9=9.9999999999999,而不是10,百度後發現double相減會轉換成二進位制,因double有效位數為 16位這就會出現儲存小數位數不夠的情況,這種情況下就會出現誤差,解決方法就是使用BigDecimal,它的有效長度足夠長可儲存 小數位數因此可代替double來進行加減乘除,下面為BigDecimal的用法:

序號

    法

型別

    述

1

public BigDecimal(double val)

構造

將double表示形式轉換

為BigDecimal

2

public BigDecimal(int val)

構造

將int表示形式轉換為

BigDecimal

3

public BigDecimal(String val)

構造

將字串表示

形式轉換為BigDecimal

4

public BigDecimal add(BigDecimal augend)

普通

加法

5

public BigDecimal subtract(BigDecimal
subtrahend)

普通

減法

6

public BigDecimal multiply(BigDecimal
multiplicand)

普通

乘法

7

public BigDecimal divide(BigDecimal
divisor)

普通

除法


  //兩個Double數相加

  public static Double add(Double v1,Double v2){

  BigDecimal b1 = new BigDecimal(v1.toString());

  BigDecimal b2 = new BigDecimal(v2.toString());

  return b1.add(b2).doubleValue();

  }


  //兩個Double數相減

  public static Double sub(Double v1,Double v2){

  BigDecimal b1 = new BigDecimal(v1.toString());

  BigDecimal b2 = new BigDecimal(v2.toString());

  return b1.subtract(b2).doubleValue();

  }


  // 兩個Double數相乘

  public static Double mul(Double v1,Double v2){

  BigDecimal b1 = new BigDecimal(v1.toString());

  BigDecimal b2 = new BigDecimal(v2.toString());

  return b1.multiply(b2).doubleValue();

  }


  //兩個Double數相除

  public static Double div(Double v1,Double v2){

  BigDecimal b1 = new BigDecimal(v1.toString());

  BigDecimal b2 = new BigDecimal(v2.toString());

  return b1.divide(b2,DEF_DIV_SCALE,BigDecimal.ROUND_HALF_UP).doubleValue();

  }


  //兩個Double數相除,並保留scale位小數

  public static Double div(Double v1,Double v2,int scale){

  if(scale<0){

  throw new IllegalArgumentException(

  "The scale must be a positive integer or zero");

  }

  BigDecimal b1 = new BigDecimal(v1.toString());

  BigDecimal b2 = new BigDecimal(v2.toString());

  return b1.divide(b2,scale,BigDecimal.ROUND_HALF_UP).doubleValue();

  }

  //進行四捨五入

   BigDecimal b1 = new BigDecimal(d);
       BigDecimal b2 = new BigDecimal(1);
        // 任何一個數字除以1都是原數字
        // ROUND_HALF_UP是BigDecimal的一個常量,
表示進行四捨五入的操作
        return b1.divide(b2, len,BigDecimal.
ROUND_HALF_UP).doubleValue();

  }

更多關於BigDecimal的用法詳見:http://www.apihome.cn/api/java/BigDecimal.html


相關文章