[java] ArithmeticException :“비 종료 소수점 확장; 정확하게 표현할 수있는 소수 결과가 없습니다”

다음 코드가 아래에 표시된 예외를 발생시키는 이유는 무엇입니까?

BigDecimal a = new BigDecimal("1.6");
BigDecimal b = new BigDecimal("9.2");
a.divide(b) // results in the following exception.

예외:

java.lang.ArithmeticException: Non-terminating decimal expansion; no exact representable decimal result.



답변

로부터 자바 (11) BigDecimal워드 프로세서 :

MathContext개체 10-0의 정밀도가 설정된 공급 (예 MathContext.UNLIMITED), 연산은 더 취하지 연산 방법이며, 정확한있는 MathContext개체. (이것은 5 이전 릴리스에서 지원 된 유일한 동작입니다.)

정확한 결과를 계산 한 결과, MathContext정밀도 설정이 0 인 객체 의 반올림 모드 설정은 사용되지 않으므로 관련이 없습니다. 나누기의 경우 정확한 몫은 무한 길이의 십진수 확장을 가질 수 있습니다. 예를 들어 1을 3으로 나눈 값입니다.

몫에 끝나지 않는 10 진수 확장이 있고 정확한 결과를 반환하도록 연산이 지정된 경우 ArithmeticException가 발생합니다. 그렇지 않으면 다른 작업에서와 같이 정확한 분할 결과가 반환됩니다.

수정하려면 다음과 같이해야합니다 .

a.divide(b, 2, RoundingMode.HALF_UP)

여기서 2는 스케일이고 RoundingMode.HALF_UP은 반올림 모드입니다.

자세한 내용은 이 블로그 게시물을 참조하십시오 .


답변

정밀도와 반올림 모드를 지정하지 않기 때문입니다. BigDecimal은 10, 20, 5000 또는 무한 소수점 자리를 사용할 수 있으며 여전히 숫자를 정확하게 표현할 수는 없다고 불평합니다. 따라서 잘못된 BigDecimal을 제공하는 대신 사용자에게 윙윙 거리는 소리입니다.

그러나 RoundingMode와 정밀도를 제공하면 (예 : 1.333333333에서 무한대를 1.3333과 같은 것으로 변환 할 수 있지만 … 프로그래머는 당신이 어떤 정밀도에 만족하는지 말할 필요가 있습니다 ‘.


답변

넌 할 수있어

a.divide(b, MathContext.DECIMAL128)

32,64,128 중에서 원하는 비트 수를 선택할 수 있습니다.

이 링크를 확인하십시오 :

http://edelstein.pebbles.cs.cmu.edu/jadeite/main.php?api=java6&state=class&package=java.math&class=MathContext


답변

이러한 문제를 해결하기 위해 아래 코드를 사용했습니다.

a.divide(b, 2, RoundingMode.HALF_EVEN)

2는 정밀도입니다. 이제 문제가 해결되었습니다.


답변

내 코드 줄이 다음과 같기 때문에 동일한 문제가 발생했습니다.

txtTotalInvoice.setText(var1.divide(var2).doubleValue() + "");

십진수 정밀도를 쓰지 않았기 때문에 이전 답변을 읽는 것으로 변경합니다.

txtTotalInvoice.setText(var1.divide(var2,4, RoundingMode.HALF_UP).doubleValue() + "");

4는 10 진법

AND RoundingMode는 Enum 상수이며,이 중 하나를 선택할 수 있습니다
UP, DOWN, CEILING, FLOOR, HALF_DOWN, HALF_EVEN, HALF_UP

이 경우 HALF_UP의 결과는 다음과 같습니다.

2.4 = 2
2.5 = 3
2.7 = 3

RoundingMode여기 에서 정보 를 확인할 수 있습니다 : http://www.javabeat.net/precise-rounding-of-decimals-using-rounding-mode-enumeration/


답변

결과를 반올림하는 문제는 나를위한 해결책은 다음과 같습니다.

divider.divide(dividend,RoundingMode.HALF_UP);


답변

BigDecimal에 대한 답변에서 ArithmeticException이 발생 함

public static void main(String[] args) {
        int age = 30;
        BigDecimal retireMentFund = new BigDecimal("10000.00");
        retireMentFund.setScale(2,BigDecimal.ROUND_HALF_UP);
        BigDecimal yearsInRetirement = new BigDecimal("20.00");
        String name = " Dennis";
        for ( int i = age; i <=65; i++){
            recalculate(retireMentFund,new BigDecimal("0.10"));
        }
        BigDecimal monthlyPension =   retireMentFund.divide(
                yearsInRetirement.divide(new BigDecimal("12"), new MathContext(2, RoundingMode.CEILING)), new MathContext(2, RoundingMode.CEILING));
        System.out.println(name+ " will have £" + monthlyPension +" per month for retirement");
    }
public static void recalculate (BigDecimal fundAmount, BigDecimal rate){
        fundAmount.multiply(rate.add(new BigDecimal("1.00")));
    }

나누기 메소드 호출에 MathContext 객체를 추가하고 정밀도 및 반올림 모드를 조정하십시오. 문제를 해결해야합니다