Skip to content
On this page

BigDecimal

Similar to BigInteger , BigDecimal can represent a floating-point number of any size with completely accurate precision.

java
BigDecimal bd = new BigDecimal("123.4567");
System.out.println(bd.multiply(bd)); // 15241.55677489

BigDecimal uses scale() to represent the number of decimal places, for example:

java
BigDecimal d1 = new BigDecimal("123.45");
BigDecimal d2 = new BigDecimal("123.4500");
BigDecimal d3 = new BigDecimal("1234500");
System.out.println(d1.scale()); // 2,two decimal places
System.out.println(d2.scale()); // 4
System.out.println(d3.scale()); // 0

Through BigDecimal 's stripTrailingZeros() method, a BigDecimal can be formatted into an equal BigDecimal but with BigDecimal trailing 0 removed:

java
BigDecimal d1 = new BigDecimal("123.4500");
BigDecimal d2 = d1.stripTrailingZeros();
System.out.println(d1.scale()); // 4
System.out.println(d2.scale()); // 2,Because 00 was removed

BigDecimal d3 = new BigDecimal("1234500");
BigDecimal d4 = d3.stripTrailingZeros();
System.out.println(d3.scale()); // 0
System.out.println(d4.scale()); // -2

If a BigDecimal 's scale() returns a negative number, for example, -2 , it means that the number is an integer and has two zeros at the end.

You can set scale of a BigDecimal . If the precision is lower than the original value, it will be rounded or truncated directly according to the specified method:

java
import java.math.BigDecimal;
import java.math.RoundingMode;

public class Main {
    public static void main(String[] args) {
        BigDecimal d1 = new BigDecimal("123.456789");
        BigDecimal d2 = d1.setScale(4, RoundingMode.HALF_UP); // to the nearest whole number,123.4568
        BigDecimal d3 = d1.setScale(4, RoundingMode.DOWN); // truncate directly,123.4567
        System.out.println(d2);
        System.out.println(d3);
    }
}

When adding, subtracting, or multiplying BigDecimal , the precision will not be lost. However, when performing division, there may be cases where the division cannot be completed. In this case, the precision and how to truncate must be specified:

java
BigDecimal d1 = new BigDecimal("123.456");
BigDecimal d2 = new BigDecimal("23.456789");
BigDecimal d3 = d1.divide(d2, 10, RoundingMode.HALF_UP); // Round to 10 decimal places
BigDecimal d4 = d1.divide(d2); // Error:ArithmeticException,Because it can’t be eliminated

You can also divide BigDecimal and find the remainder at the same time:

java
import java.math.BigDecimal;

public class Main {
    public static void main(String[] args) {
        BigDecimal n = new BigDecimal("12.345");
        BigDecimal m = new BigDecimal("0.12");
        BigDecimal[] dr = n.divideAndRemainder(m);
        System.out.println(dr[0]); // 102
        System.out.println(dr[1]); // 0.105
    }
}

When divideAndRemainder() method is called, the returned array contains two BigDecimal , which are the quotient and the remainder. The quotient is always an integer, and the remainder will not be greater than the divisor. We can use this method to determine whether two BigDecimal are multiples of integers:

java
BigDecimal n = new BigDecimal("12.75");
BigDecimal m = new BigDecimal("0.15");
BigDecimal[] dr = n.divideAndRemainder(m);
if (dr[1].signum() == 0) {
    // n is an integer multiple of m
}

Compare BigDecimal

When comparing whether the values of two BigDecimal are equal, special attention should be paid to the fact that using equals() method not only requires the values of the two BigDecimal to be equal, but also requires their scale() to be equal:

java
BigDecimal d1 = new BigDecimal("123.456");
BigDecimal d2 = new BigDecimal("123.45600");
System.out.println(d1.equals(d2)); // false,Because the scale is different
System.out.println(d1.equals(d2.stripTrailingZeros())); // true,Because after d2 removes the tail 0, the scale becomes 3
System.out.println(d1.compareTo(d2)); // 0 = equal, -1 = d1 < d2, 1 = d1 > d2

compareTo() method must be used for comparison. It returns negative numbers, positive numbers and 0 respectively according to the size of the two values, indicating less than, greater than and equal to respectively.

Notice

Always use compareTo() to compare the values of two BigDecimals, do not use equals()!

If you look at the source code of BigDecimal , you can find that a BigDecimal is actually represented by a BigInteger and a scale , that is, BigInteger represents a complete integer, and scale represents the number of decimal places:

java
public class BigDecimal extends Number implements Comparable<BigDecimal> {
    private final BigInteger intVal;
    private final int scale;
}

BigDecimal also inherits from Number and is an immutable object.

Summary

BigDecimal is used to represent precise decimals and is often used in financial calculations;

To compare BigDecimal values for equality, you must use compareTo() instead of equals() .

BigDecimal has loaded