【 Android 】float / double 計算失去精度

今天在數值運算的時候,發現一個問題:
getValue = 1619;
seekbarInvalue = getValue * 0.01;

seekbarInvalue += 0.1;
運算出來的結果是:

為什麼浮點數會失去精度?
A: 二進制表示可能不夠精確,浮點數值沒辦法用十進制來精確表示的原因可能是cpu表示的浮點數的方法,若是這樣就需要在運算的時候犧牲一些精度; 例如2.4的二進制表示並非是2.4,而是最接近的表示是2.3999999999999999。

您可以使用Binary Coded Decimal (BCD)来保持精度。BCD數字編碼方法會把每一个十進制數字單獨編碼;BCD碼的主要優點是在機器格式與人可讀的格式之間轉換容易,以及十進制數值的高精度表示。BCD碼的主要缺點是增加了實現算術運算的電路的複雜度,以及儲存效率低。

而在android裡有以下方法可以運算浮點數:
1. Math.round(value*100)/100.0;  
//返回x最接近的整数,如果x的小数部分大于等于0.5,返回值是大于x的最小整数,否则round函数返回小于等于x的最大整数

2. Math.floor(seekbarInvalue*100)/100.0; 
//Math.floor()方法會傳回小於或等於給定數值(輸入參數)的最大整數。

3. DecimalFormat df = new DecimalFormat("#0.00");
  double Value = new Double(df.format(value));
//DecimalFormat用法

4. 使用math.BigDecimal 的運算是精度較高的方式,並且一定要轉作string

/**
     * 提供精确的加法运算。
     * @param v1 被加数
     * @param v2 加数
     * @return 两个参数的和
     */
    public static double add(double v1,double v2){
        BigDecimal b1 = new BigDecimal(Double.toString(v1));
        BigDecimal b2 = new BigDecimal(Double.toString(v2));
        return b1.add(b2).doubleValue();
    }
    /**
     * 提供精确的减法运算。
     * @param v1 被减数
     * @param v2 减数
     * @return 两个参数的差
     */
    public static double sub(double v1,double v2){
        BigDecimal b1 = new BigDecimal(Double.toString(v1));
        BigDecimal b2 = new BigDecimal(Double.toString(v2));
        return b1.subtract(b2).doubleValue();
    } 
    /**
     * 提供精确的乘法运算。
     * @param v1 被乘数
     * @param v2 乘数
     * @return 两个参数的积
     */
    public static double mul(double v1,double v2){
        BigDecimal b1 = new BigDecimal(Double.toString(v1));
        BigDecimal b2 = new BigDecimal(Double.toString(v2));
        return b1.multiply(b2).doubleValue();
    }

    /**
     * 提供(相对)精确的除法运算,当发生除不尽的情况时,精确到
     * 小数点以后10位,以后的数字四舍五入。
     * @param v1 被除数
     * @param v2 除数
     * @return 两个参数的商
     */
    public static double div(double v1,double v2){
        return div(v1,v2,DEF_DIV_SCALE);
    }

留言

這個網誌中的熱門文章

【 Android 】控制ImageView大小&位置

【 Android 】利用file取得資料夾內檔案

【 Android 】防止系統進入休眠和螢幕恆亮