SoEasy——java保留小數位問題

  • java保留兩位小數問題:補充(double)(Math.round(result_value*10000)/10000.0)(double)(Math.round(result_value*10000)/10000.0)這樣計算可以保留result_value小數點後四位,以此類推,1後面幾個零就是保留小數點後幾位數.方式一:四捨五入doublef=111231.5585;BigDecimalb=newBigDecimal(f);doublef1=b.setScale(2,
  • java保留兩位小數問題:
  • 補充
  • (double)(Math.round(result_value*10000)/10000.0)
  • (double)(Math.round(result_value*10000)/10000.0)
  • 這樣計算可以保留result_value小數點後四位,以此類推,1後面幾個零就是保留小數點後幾位數.
  • 方式一:
  • 四捨五入
  • double f = 111231.5585;
  • BigDecimal b = new BigDecimal(f);
  • double f1 = b.setScale(2, BigDecimal.ROUND_HALF_UP).doubleValue();
  • 保留兩位小數
  • ---------------------------------------------------------------
  • 方式二:
  • java.text.DecimalFormat df =new java.text.DecimalFormat("#.00");
  • df.format(你要格式化的數字);
  • 例:new java.text.DecimalFormat("#.00").format(3.1415926)
  • #.00 表示兩位小數 #.0000四位小數 以此類推...
  • 方式三:
  • double d = 3.1415926;
  • String result = String .format("%.2f");
  • %.2f %. 表示 小數點前任意位數 2 表示兩位小數 格式後的結果為f 表示浮點型
  • 方式四:
  • NumberFormat ddf1=NumberFormat.getNumberInstance() ;
  • void setMaximumFractionDigits(int digits)
  • digits 顯示的數字位數
  • 為格式化對象設定小數點後的顯示的最多位,顯示的最後位是舍入的
  • import java.text.* ;
  • import java.math.* ;
  • class TT
  • {
  • public static void main(String args[])
  • { double x=23.5455;
  • NumberFormat ddf1=NumberFormat.getNumberInstance() ;
  • ddf1.setMaximumFractionDigits(2);
  • String s= ddf1.format(x) ;
  • System.out.print(s);
  • }
  • }
  • ---------------------------------------------------------------------------------------------------------
  • 有一篇:
  • (1)、浮點數精確計算
  • 勝利油田三流合一項目中一直存在一個問題,就是每次報表統計的物資金額和實際的金額要差那麼幾分錢,和實際金額不一致,讓客戶覺得總是不那麼舒服,原因是因為我們使用java的浮點類型double來定義物資金額,並且在報表統計中我們經常要進行一些運算,但Java中浮點數(double、float)的計算是非精確計算,請看下面一個例子:
  • System.out.println(0.05 + 0.01);
  • System.out.println(1.0 - 0.42);
  • System.out.println(4.015 * 100);
  • System.out.println(123.3 / 100);
  • 你的期望輸出是什麼?可實際的輸出確實這樣的:
  • 0.060000000000000005
  • 0.5800000000000001
  • 401.49999999999994
  • 1.2329999999999999
  • 這個問題就非常嚴重了,如果你有123.3元要購買商品,而計算機卻認為你只有123.29999999999999元,錢不夠,計算機拒絕交易。
  • (2)、四捨五入
  • 是否可以四捨五入呢?當然可以,習慣上我們本能就會這樣考慮,但四捨五入意味著誤差,商業運算中可能意味著錯誤,同時Java中也沒有提供保留指定位數的四捨五入方法,只提供了一個Math.round(double d)和Math.round(float f)的方法,分別返回長整型和整型值。round方法不能設置保留幾位小數,我們只能象這樣(保留兩位):
  • public double round(double value){
  • return Math.round( value * 100 ) / 100.0;
  • }
  • 但非常不幸的是,上面的代碼並不能正常工作,給這個方法傳入4.015它將返回4.01而不是4.02,如我們在上面看到的
  • 4.015 * 100 = 401.49999999999994
  • 因此如果我們要做到精確的四捨五入,這種方法不能滿足我們的要求。
  • 還有一種方式是使用java.text.DecimalFormat,但也存在問題,format採用的舍入模式是ROUND_HALF_DOWN(舍入模式在下面有介紹),比如說4.025保留兩位小數會是4.02,因為.025距離” nearest neighbor”(.02和.03)長度是相等,向下舍入就是.02,如果是4.0251那麼保留兩位小數就是4.03。
  • System.out.println(new java.text.DecimalFormat("0.00").format(4.025));
  • System.out.println(new java.text.DecimalFormat("0.00").format(4.0251));
  • 輸出是
  • 4.02
  • 4.03
  • (3)、浮點數輸出(科學記數法)
  • Java浮點型數值在大於9999999.0就自動轉化為科學記數法來表示,我們看下面的例子:
  • System.out.println(999999999.04);
  • System.out.println(99999999.04);
  • System.out.println(10000000.01);
  • System.out.println(9999999.04);
  • 輸出的結果如下:
  • 9.9999999904E8
  • 9.999999904E7
  • 1.000000001E7
  • 9999999.04
  • 但有時我們可能不需要科學記數法的表示方法,需要轉換為字符串,還不能直接用toString()等方法轉換,很煩瑣。
  • BigDecimal介紹
  • BigDecimal是Java提供的一個不變的、任意精度的有符號十進制數對象。它提供了四個構造器,有兩個是用BigInteger構造,在這裡我們不關心,我們重點看用double和String構造的兩個構造器(有關BigInteger詳細介紹請查閱j2se API文檔)。
  • BigDecimal(double val)
  • Translates a double into a BigDecimal.
  • BigDecimal(String val)
  • Translates the String representation of a BigDecimal into a BigDecimal.
  • BigDecimal(double)是把一個double類型十進制數構造為一個BigDecimal對象實例。
  • BigDecimal(String)是把一個以String表示的BigDecimal對象構造為BigDecimal對象實例。
  • 習慣上,對於浮點數我們都會定義為double或float,但BigDecimal API文檔中對於BigDecimal(double)有這麼一段話:
  • Note: the results of this constructor can be somewhat unpredictable. One might assume that new BigDecimal(.1) is exactly equal to .1, but it is actually equal to .10000000000000000555111512312578 27021181583404541015625. This is so because .1 cannot be represented exactly as a double (or, for that matter, as a binary fraction of any finite length). Thus, the long value that is being passed in to the constructor is not exactly equal to .1, appearances notwithstanding.
  • The (String) constructor, on the other hand, is perfectly predictable: new BigDecimal(".1") is exactly equal to .1, as one would expect. Therefore, it is generally recommended that the (String) constructor be used in preference to this one
  • 下面對這段話做簡單解釋:
  • 注意:這個構造器的結果可能會有不可預知的結果。有人可能設想new BigDecimal(.1)等於.1是正確的,但它實際上是等於.1000000000000000055511151231257827021181583404541015625,這就是為什麼.1不能用一個double精確表示的原因,因此,這個被放進構造器中的長值並不精確的等於.1,儘管外觀看起來是相等的。
  • 然而(String)構造器,則完全可預知的,new BigDecimal(“.1”)如同期望的那樣精確的等於.1,因此,(String)構造器是被優先推薦使用的。

轉自https://www.aliyun.com/jiaocheng/240346.html?spm=5176.100033.9.27.248a52e18ApiAE


分享到:


相關文章: