Java Language
BigDecimal
Zoeken…
Invoering
De BigDecimal- klasse biedt bewerkingen voor rekenen (optellen, aftrekken, vermenigvuldigen, delen), schaalmanipulatie, afronding, vergelijking, hashing en formaatconversie. De BigDecimal staat voor onveranderlijke, met willekeurige precisie ondertekende decimale getallen. Deze klasse moet worden gebruikt voor een hoge nauwkeurigheidsberekening.
BigDecimal-objecten zijn onveranderlijk
Als u met BigDecimal wilt berekenen, moet u de geretourneerde waarde gebruiken omdat BigDecimal-objecten onveranderlijk zijn:
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
BigDecimals vergelijken
De methode compareTo
moet worden gebruikt om BigDecimals
te vergelijken:
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
Gewoonlijk moet u de methode is equals
niet gebruiken, omdat deze twee BigDecimals
alleen als gelijk beschouwt als ze in waarde gelijk zijn en ook schaal :
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
Wiskundige bewerkingen met BigDecimal
Dit voorbeeld laat zien hoe u elementaire wiskundige bewerkingen uitvoert met BigDecimals.
1.Addition
BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");
//Equivalent to result = a + b
BigDecimal result = a.add(b);
System.out.println(result);
Resultaat: 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);
Resultaat: -2
3.Multiplication
Bij het vermenigvuldigen van twee BigDecimal
s krijgt het resultaat een schaal gelijk aan de som van de schalen van operanden.
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);
Resultaat: 36.89931
Om de schaal van het resultaat te wijzigen, gebruikt u de overbelaste vermenigvuldigingsmethode waarmee MathContext
kan worden doorgegeven - een object dat de regels voor operators beschrijft, met name de precisie en de afrondingsmodus van het resultaat. Raadpleeg de Oracle-documentatie voor meer informatie over de beschikbare afrondingsmodi.
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);
Resultaat: 36,90
4.Division
De deling is iets gecompliceerder dan de andere rekenkundige bewerkingen, denk bijvoorbeeld aan het onderstaande voorbeeld:
BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");
BigDecimal result = a.divide(b);
System.out.println(result);
We zouden verwachten dat dit iets zou geven dat lijkt op: 0.7142857142857143, maar we zouden krijgen:
Resultaat: java.lang.ArithmeticException: niet-terminerende decimale expansie; geen exact representeerbaar decimaal resultaat.
Dit zou perfect werken als het resultaat een afsluitende decimaal zou zijn, zeg maar als ik 5 door 2 wilde delen, maar voor die getallen die bij het delen een niet-afsluitend resultaat zouden geven, zouden we een ArithmeticException
. In het echte scenario kan men de waarden die tijdens de deling zouden voorkomen, niet voorspellen, dus moeten we de schaal en de afrondingsmodus voor BigDecimal-deling opgeven. Raadpleeg de Oracle-documentatie voor meer informatie over de schaal- en afrondingsmodus.
Ik zou bijvoorbeeld kunnen doen:
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);
Resultaat: 0,7142857143
5. Rest of Modulus
BigDecimal a = new BigDecimal("5");
BigDecimal b = new BigDecimal("7");
//Equivalent to result = a % b
BigDecimal result = a.remainder(b);
System.out.println(result);
Resultaat: 5
6.Power
BigDecimal a = new BigDecimal("5");
//Equivalent to result = a^10
BigDecimal result = a.pow(10);
System.out.println(result);
Resultaat: 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);
Resultaat: 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);
Resultaat: 5
9. Verplaats naar links
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);
Resultaat: 52.3449843776
10. Verplaats naar rechts
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);
Resultaat: 5234498.43776
Er zijn veel meer opties en een combinatie van parameters voor de bovengenoemde voorbeelden (er zijn bijvoorbeeld 6 variaties van de verdeelmethode), deze set is een niet-uitputtende lijst en bevat een paar basisvoorbeelden.
BigDecimal gebruiken in plaats van float
Vanwege de manier waarop het float-type in het computergeheugen wordt weergegeven, kunnen de resultaten van bewerkingen met dit type onnauwkeurig zijn - sommige waarden worden als benaderingen opgeslagen. Goede voorbeelden hiervan zijn monetaire berekeningen. Als hoge precisie nodig is, moeten andere typen worden gebruikt. Java 7 biedt bijvoorbeeld 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));
}
De output van dit programma is:
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
Voor een beginsaldo van 10000,00, na 1000 bewerkingen voor 1,99, verwachten we dat het saldo 8010,00 is. Het gebruik van het float-type geeft ons een antwoord rond 8009.77, wat onaanvaardbaar onnauwkeurig is in het geval van monetaire berekeningen. Het gebruik van BigDecimal geeft ons het juiste resultaat.
BigDecimal.valueOf ()
De klasse BigDecimal bevat een interne cache van veelgebruikte getallen, bijvoorbeeld 0 tot 10. De methoden BigDecimal.valueOf () worden bij voorkeur gegeven aan constructeurs met vergelijkbare typeparameters, dwz in het onderstaande voorbeeld heeft a de voorkeur boven 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
Initialisatie van BigDecimals met waarde nul, één of tien
BigDecimal biedt statische eigenschappen voor de getallen nul, één en tien. Het is een goede gewoonte om deze te gebruiken in plaats van de werkelijke cijfers te gebruiken:
Door de statische eigenschappen te gebruiken, voorkomt u een onnodige instantiëring, ook hebt u een letterlijke code in plaats van een 'magisch getal'.
//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;