Buscar..


Introducción

La clase BigDecimal proporciona operaciones para aritmética (sumar, restar, multiplicar, dividir), manipulación de escala, redondeo, comparación, hash y conversión de formato. El BigDecimal representa números decimales firmados de precisión arbitraria e inmutables. Esta clase se utilizará en una necesidad de cálculo de alta precisión.

Los objetos BigDecimal son inmutables.

Si desea calcular con BigDecimal, tiene que usar el valor devuelto porque los objetos BigDecimal son inmutables:

BigDecimal a = new BigDecimal("42.23");
BigDecimal b = new BigDecimal("10.001");

a.add(b); // a will still be 42.23

BigDecimal c = a.add(b); // c will be 52.231 

Comparando BigDecimals

El método compareTo debe usarse para comparar BigDecimals :

BigDecimal a = new BigDecimal(5);
a.compareTo(new BigDecimal(0));    // a is greater, returns 1
a.compareTo(new BigDecimal(5));    // a is equal, returns 0
a.compareTo(new BigDecimal(10));   // a is less, returns -1

Comúnmente no se debe utilizar la equals método ya que considera dos BigDecimals iguales sólo si son iguales en valor y también de la escala:

BigDecimal a = new BigDecimal(5);
a.equals(new BigDecimal(5));       // value and scale are equal, returns true
a.equals(new BigDecimal(5.00));    // value is equal but scale is not, returns false

Operaciones matemáticas con BigDecimal.

Este ejemplo muestra cómo realizar operaciones matemáticas básicas con BigDecimals.

1.Adición

BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");

//Equivalent to result = a + b
BigDecimal result = a.add(b);
System.out.println(result);

Resultado: 12

2.Subtraction

BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");

//Equivalent to result = a - b
BigDecimal result = a.subtract(b);
System.out.println(result);

Resultado: -2

3.Multiplicacion

Al multiplicar dos BigDecimal s, el resultado tendrá una escala igual a la suma de las escalas de los operandos.

BigDecimal a = new BigDecimal("5.11");
BigDecimal b = new BigDecimal("7.221");

//Equivalent to result = a * b
BigDecimal result = a.multiply(b);
System.out.println(result);

Resultado: 36.89931

Para cambiar la escala del resultado, utilice el método de multiplicación sobrecargada que permite pasar MathContext , un objeto que describe las reglas para los operadores, en particular la precisión y el modo de redondeo del resultado. Para obtener más información sobre los modos de redondeo disponibles, consulte la documentación de Oracle.

BigDecimal a = new BigDecimal("5.11");
BigDecimal b = new BigDecimal("7.221");

MathContext returnRules = new MathContext(4, RoundingMode.HALF_DOWN);

//Equivalent to result = a * b
BigDecimal result = a.multiply(b, returnRules);
System.out.println(result);

Resultado: 36.90

4.Division

La división es un poco más complicada que las otras operaciones aritméticas, por ejemplo, considere el siguiente ejemplo:

BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");

BigDecimal result = a.divide(b);
System.out.println(result);

Esperamos que esto dé algo similar a: 0.7142857142857143, pero obtendríamos:

Resultado: java.lang.ArithmeticException: Expansión decimal sin terminación; No hay un resultado decimal representable exacto.

Esto funcionaría perfectamente bien cuando el resultado fuera un decimal de terminación, por ejemplo, si quisiera dividir 5 por 2, pero para aquellos números que al dividir darían un resultado no final, obtendríamos una ArithmeticException . En el escenario del mundo real, uno no puede predecir los valores que se encontrarían durante la división, por lo que necesitamos especificar la Escala y el Modo de redondeo para la división BigDecimal. Para obtener más información sobre la escala y el modo de redondeo, consulte la documentación de Oracle .

Por ejemplo, podría hacer:

BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");

//Equivalent to result = a / b (Upto 10 Decimal places and Round HALF_UP)
BigDecimal result = a.divide(b,10,RoundingMode.HALF_UP);
System.out.println(result);

Resultado: 0.7142857143

5.El resto o módulo

BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");

//Equivalent to result = a % b
BigDecimal result = a.remainder(b);
System.out.println(result);

Resultado: 5

6. Poder

BigDecimal a = new BigDecimal("5");

//Equivalent to result = a^10    
BigDecimal result = a.pow(10);
System.out.println(result);

Resultado: 9765625

7.Max

BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");

//Equivalent to result = MAX(a,b) 
BigDecimal result = a.max(b);
System.out.println(result);

Resultado: 7

8.Min

BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");

//Equivalent to result = MIN(a,b) 
BigDecimal result = a.min(b);
System.out.println(result);

Resultado: 5

9. Mover punto a la izquierda

BigDecimal a = new BigDecimal("5234.49843776");

//Moves the decimal point to 2 places left of current position
BigDecimal result = a.movePointLeft(2);
System.out.println(result);

Resultado: 52.3449843776

10. Mover punto a la derecha

BigDecimal a = new BigDecimal("5234.49843776");

//Moves the decimal point to 3 places right of current position
BigDecimal result = a.movePointRight(3);
System.out.println(result);

Resultado: 5234498.43776

Existen muchas más opciones y una combinación de parámetros para los ejemplos mencionados anteriormente (por ejemplo, hay 6 variaciones del método de división), este conjunto no es una lista exhaustiva y cubre algunos ejemplos básicos.

Usando BigDecimal en lugar de flotar

Debido a la forma en que el tipo flotante se representa en la memoria de la computadora, los resultados de las operaciones que utilizan este tipo pueden ser inexactos, algunos valores se almacenan como aproximaciones. Buenos ejemplos de esto son los cálculos monetarios. Si es necesaria una alta precisión, deben usarse otros tipos. por ejemplo, Java 7 proporciona BigDecimal.

import java.math.BigDecimal;

public class FloatTest {

public static void main(String[] args) {
    float accountBalance = 10000.00f;
    System.out.println("Operations using float:");
    System.out.println("1000 operations for 1.99");
    for(int i = 0; i<1000; i++){
        accountBalance -= 1.99f;
    }
    System.out.println(String.format("Account balance after float operations: %f", accountBalance));
    
    BigDecimal accountBalanceTwo = new BigDecimal("10000.00");
    System.out.println("Operations using BigDecimal:");
    System.out.println("1000 operations for 1.99");
    BigDecimal operation = new BigDecimal("1.99");
    for(int i = 0; i<1000; i++){
        accountBalanceTwo = accountBalanceTwo.subtract(operation);
    }
    System.out.println(String.format("Account balance after BigDecimal operations: %f", accountBalanceTwo));
}

La salida de este programa es:

Operations using float:
1000 operations for 1.99
Account balance after float operations: 8009,765625
Operations using BigDecimal:
1000 operations for 1.99
Account balance after BigDecimal operations: 8010,000000

Para un saldo inicial de 10000.00, después de 1000 operaciones por 1.99, esperamos que el saldo sea 8010.00. El uso del tipo de coma flotante nos da una respuesta en torno al 8009.77, lo que es inaceptablemente impreciso en el caso de los cálculos monetarios. Usar BigDecimal nos da el resultado adecuado.

BigDecimal.valueOf ()

La clase BigDecimal contiene un caché interno de los números utilizados con frecuencia, por ejemplo, de 0 a 10. Los métodos BigDecimal.valueOf () se proporcionan con preferencia a los constructores con parámetros de tipo similar, es decir, en el ejemplo siguiente se prefiere a b.

BigDecimal a = BigDecimal.valueOf(10L); //Returns cached Object reference
BigDecimal b = new BigDecimal(10L); //Does not return cached Object reference

BigDecimal a = BigDecimal.valueOf(20L); //Does not return cached Object reference
BigDecimal b = new BigDecimal(20L); //Does not return cached Object reference


BigDecimal a = BigDecimal.valueOf(15.15); //Preferred way to convert a double (or float) into a BigDecimal, as the value returned is equal to that resulting from constructing a BigDecimal from the result of using Double.toString(double)
BigDecimal b = new BigDecimal(15.15); //Return unpredictable result

Inicialización de BigDecimals con valor cero, uno o diez.

BigDecimal proporciona propiedades estáticas para los números cero, uno y diez. Es una buena práctica usar estos en lugar de usar los números reales:

Al usar las propiedades estáticas, evitas una creación de instancias innecesaria, también tienes un literal en tu código en lugar de un 'número mágico'.

//Bad example:
BigDecimal bad0 = new BigDecimal(0);
BigDecimal bad1 = new BigDecimal(1);
BigDecimal bad10 = new BigDecimal(10);

//Good Example:
BigDecimal good0 = BigDecimal.ZERO;
BigDecimal good1 = BigDecimal.ONE;
BigDecimal good10 = BigDecimal.TEN;


Modified text is an extract of the original Stack Overflow Documentation
Licenciado bajo CC BY-SA 3.0
No afiliado a Stack Overflow