8

次の Java のコード スニペットを見てみましょう。

package division;

import java.math.BigDecimal;

final public class Main
{
    public static void main(String[] args)
    {
        BigDecimal a = new BigDecimal(2);
        BigDecimal b = new BigDecimal(3);

        System.out.println(a.multiply(b));
        System.out.println(a.add(b));
        System.out.println(b.subtract(a));
        System.out.println(a.divide(b));
    }
}

上記のコード スニペットでは、最後の操作 (除算) を除くすべての操作が正常に実行されます。BigDecimalJava で2 つの数値を除算しようとすると、 java.lang.ArithmeticException. なんで?この問題の解決策は何ですか?

4

4 に答える 4

15

BigDecimal#divide(BigDecimal)ドキュメントから:

...正確な商を表すことができない場合 (終了しない 10 進展開があるため)、ArithmeticException がスローされます。

あなたの特定のケースでは、「2/3」には非終了の10進展開(0.6666 ...)があるためdivide()、スケールを取る形式を使用するかRoundingMode、無限表現を解決する必要があります。例えば:

BigDecimal a = new BigDecimal(2);
BigDecimal b = new BigDecimal(3);
a.divide(b, 4, RoundingMode.CEILING); // => 0.6667
a.divide(b, 4, RoundingMode.FLOOR);   // => 0.6666
于 2012-04-05T17:11:42.947 に答える
2

除算の結果の正確な表現がないため、例外が発生します。この問題を回避するには、次のようにスケールと丸めモードでオーバーロードを使用する必要があります。

System.out.println(a.divide(b, 20, RoundingMode.HALF_UP));

ideoneの変更されたコードは次のとおりです。

6
5
1
0.66666666666666666667
于 2012-04-05T17:13:57.377 に答える
1

javadocを読むとjava.lang.ArithmeticException、正確な商に終端の 10 進数展開がない場合にスローされると書かれています。2/3 = .666666666... 終了しません

于 2012-04-05T17:12:03.443 に答える
1

値が (this / divisor) で、優先スケールが (this.scale() - divisor.scale()) である BigDecimal を返します。正確な商を表すことができない場合 (終了しない 10 進展開があるため)、ArithmeticException がスローされます。

2 / 3 = 0.666666666666666666666........ などとなり、表現できません。JavaDoc が言うように、それは非終了の10進展開です

于 2012-04-05T17:12:08.873 に答える