BigDecimal 運算及取小數位

 一、介紹 

     Java在java.math包中提供的API類BigDecimal,用來對超過16位有效位的數進行精確的運算。雙精度浮點型變量double可以處理16位有效數。在實際應用中,需要對更大或者更小的數進行運算和處理。float和double只能用來做科學計算或者是工程計算,在商業計算中要用java.math.BigDecimal。BigDecimal所創建的是對象,我們不能使用傳統的+、-、*、/等算術運算符直接對其對象進行數學運算,而必須調用其相對應的方法。方法中的參數也必須是BigDecimal的對象。構造器是類的特殊方法,專門用來創建對象,特別是帶有參數的對象。

二、構造器描述

BigDecimal(int)           創建一個具有參數所指定整數值的對象。
BigDecimal(double)    創建一個具有參數所指定雙精度值的對象。
BigDecimal(long)        創建一個具有參數所指定長整數值的對象。
BigDecimal(String)      創建一個具有參數所指定以字符串表示的數值的對象。

三、運算方法描述

add(BigDecimal)        BigDecimal對象中的值相加,然後返回這個對象。
subtract(BigDecimal) BigDecimal對象中的值相減,然後返回這個對象。
multiply(BigDecimal)  BigDecimal對象中的值相乘,然後返回這個對象。
divide(BigDecimal)     BigDecimal對象中的值相除,然後返回這個對象。
toString()                將BigDecimal對象的數值轉換成字符串。
doubleValue()          將BigDecimal對象中的值以雙精度數返回。
floatValue()             將BigDecimal對象中的值以單精度數返回。
longValue()             將BigDecimal對象中的值以長整數返回。
intValue()               將BigDecimal對象中的值以整數返回。

下面是一個工具類,該工具類提供加,減,乘,除運算。

public class Arith {  
    /** 
     * 提供精確加法計算的add方法 
     * @param value1 被加數 
     * @param value2 加數 
     * @return 兩個參數的和 
     */  
    public static double add(double value1,double value2){  
        BigDecimal b1 = new BigDecimal(Double.valueOf(value1));  
        BigDecimal b2 = new BigDecimal(Double.valueOf(value2));  
        return b1.add(b2).doubleValue();  
    }  
      
    /** 
     * 提供精確減法運算的sub方法 
     * @param value1 被減數 
     * @param value2 減數 
     * @return 兩個參數的差 
     */  
    public static double sub(double value1,double value2){  
        BigDecimal b1 = new BigDecimal(Double.valueOf(value1));  
        BigDecimal b2 = new BigDecimal(Double.valueOf(value2));  
        return b1.subtract(b2).doubleValue();  
    }  
      
    /** 
     * 提供精確乘法運算的mul方法 
     * @param value1 被乘數 
     * @param value2 乘數 
     * @return 兩個參數的積 
     */  
    public static double mul(double value1,double value2){  
        BigDecimal b1 = new BigDecimal(Double.valueOf(value1));  
        BigDecimal b2 = new BigDecimal(Double.valueOf(value2));  
        return b1.multiply(b2).doubleValue();  
    }  
      
    /** 
     * 提供精確的除法運算方法div 
     * @param value1 被除數 
     * @param value2 除數 
     * @param scale 精確範圍 
     * @return 兩個參數的商 
     * @throws IllegalAccessException 
     */  
    public static double div(double value1,double value2,int scale) throws IllegalAccessException{  
        //如果精確範圍小於0,拋出異常信息  
        if(scale<0){           
            throw new IllegalAccessException("精確度不能小於0");  
        }  
        BigDecimal b1 = new BigDecimal(Double.valueOf(value1));  
        BigDecimal b2 = new BigDecimal(Double.valueOf(value2));  
        return b1.divide(b2, scale).doubleValue();      
    }  
} 

四、常用方法集錦

scale()   小數點後的位數

BigDecimal.setScale()方法用於格式化小數點
setScale(1)表示保留一位小數,默認用四捨五入方式 
setScale(1,BigDecimal.ROUND_DOWN)直接刪除多餘的小數位,如2.35會變成2.3 
setScale(1,BigDecimal.ROUND_UP)進位處理(進一法),2.35變成2.4 
setScale(1,BigDecimal.ROUND_HALF_UP)四捨五入,2.35變成2.4

setScaler(1,BigDecimal.ROUND_HALF_DOWN)四捨五入,2.35變成2.3,如果是5則向下舍

setScaler(1,BigDecimal.ROUND_CEILING)接近正無窮大的舍入

setScaler(1,BigDecimal.ROUND_FLOOR)接近負無窮大的舍入,數字>0和ROUND_UP作用一樣,數字<0和ROUND_DOWN作用一樣

setScaler(1,BigDecimal.ROUND_HALF_EVEN)向最接近的數字舍入,如果與兩個相鄰數字的距離相等,則向相鄰的偶數舍入。

五、格式化

       NumberFormat是所有數值格式的抽象基類。此類提供格式化和解析數值的接口,可用於格式化和解析任何語言環境的數值。使代碼能夠完全獨立於小數點、千位分隔符甚至所用特定小數位數的語言環境約定,並與數值格式是否爲偶小數無關。

getInstance 或 getNumberInstance 獲取常規數值格式。
getIntegerInstance 只保留整數數值格式。
getCurrencyInstance 獲取貨幣數值格式。
getPercentInstance 獲取顯示百分比的格式。使用此格式,小數 0.53 將顯示爲 53%。
setMinimumFractionDigits 控制數值的顯示。
 

/** 
 * 格式化 
 */  
@Test  
public void test3() {  
    NumberFormat currency = NumberFormat.getCurrencyInstance(); //建立貨幣格式化引用  
    NumberFormat percent = NumberFormat.getPercentInstance();  //建立百分比格式化引用  
    percent.setMaximumFractionDigits(3); //百分比小數點最多3位  
  
    BigDecimal loanAmount = new BigDecimal("150.48"); //貸款金額  
    BigDecimal interestRate = new BigDecimal("0.008"); //利率  
    BigDecimal interest = loanAmount.multiply(interestRate); //相乘  
  
    System.out.println("貸款金額:\t" + currency.format(loanAmount)); //貸款金額: ¥150.48  
    System.out.println("利率:\t" + percent.format(interestRate));  //利率: 0.8%  
    System.out.println("利息:\t" + currency.format(interest)); //利息: ¥1.20  
}  
@Test  
public void test3() {  
    DecimalFormat df = new DecimalFormat();  
    double data = 1234.56789; //格式化之前的數字  
    //1、定義要顯示的數字的格式(這種方式會四捨五入)  
    String style = "0.0";  
    df.applyPattern(style);  
    System.out.println("1-->" + df.format(data));  //1234.6  
  
    //2、在格式後添加諸如單位等字符  
    style = "00000.000 kg";  
    df.applyPattern(style);  
    System.out.println("2-->" + df.format(data));  //01234.568 kg  
  
    //3、 模式中的"#"表示如果該位存在字符,則顯示字符,如果不存在,則不顯示。  
    style = "##000.000 kg";  
    df.applyPattern(style);  
    System.out.println("3-->" + df.format(data));  //1234.568 kg  
  
    //4、 模式中的"-"表示輸出爲負數,要放在最前面  
    style = "-000.000";  
    df.applyPattern(style);  
    System.out.println("4-->" + df.format(data)); //-1234.568  
 
    //5、 模式中的","在數字中添加逗號,方便讀數字  
    style = "-0,000.0#";  
    df.applyPattern(style);  
    System.out.println("5-->" + df.format(data));  //5-->-1,234.57  
  
    //6、模式中的"E"表示輸出爲指數,"E"之前的字符串是底數的格式,  
    // "E"之後的是字符串是指數的格式  
    style = "0.00E000";  
    df.applyPattern(style);  
    System.out.println("6-->" + df.format(data));  //6-->1.23E003  
  
    //7、 模式中的"%"表示乘以100並顯示爲百分數,要放在最後。  
    style = "0.00%";  
    df.applyPattern(style);  
    System.out.println("7-->" + df.format(data));  //7-->123456.79%  
  
    //8、 模式中的"\u2030"表示乘以1000並顯示爲千分數,要放在最後。  
    style = "0.00\u2030";  
    //在構造函數中設置數字格式  
    DecimalFormat df1 = new DecimalFormat(style);  
    //df.applyPattern(style);  
    System.out.println("8-->" + df1.format(data));  //8-->1234567.89‰  
}  

六、比較大小

BigDecimal是通過使用compareTo(BigDecimal)來進行兩個BigDecimal比較的

public void testCompare(){
   BigDecimal a=new BigDecimal("20");
   a.compareTo(b)==1;   //a>b
   a.compareTo(b)==-1;  //a<b
   a.compareTo(b)==0;   //a=b
   a.compareTo(b)<1;    //a<=b
   a.compareTo(b)>-1;   //a>=b

}

6.1 科學計數法

@Test  
public void test5() {  
    BigDecimal bd = new BigDecimal("3.40256010353E11");  
    String result = bd.toPlainString();  
    System.out.println(result);  //340256010353  
}  

6.2  處理價格中逗號

@Test  
public void test1() {  
    java.util.StringTokenizer st = new StringTokenizer( "123,456,789", ",");  
    StringBuffer sb = new StringBuffer();  
    while(st.hasMoreTokens())   {  
        sb.append(st.nextToken());  
    }  
    System.out.println(sb);  //123456789  
}  
  
@Test  
public void test2() {  
    String str = "123,456,789";  
    str = str.replace(",", "");  
    System.out.println(str);  //123456789  
}  

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章