176

I want to do some simple sums with some currency values expressed in BigDecimal type.

BigDecimal test = new BigDecimal(0);
System.out.println(test);
test.add(new BigDecimal(30));
System.out.println(test);
test.add(new BigDecimal(45));
System.out.println(test);

Obviously I do not understand well the BigDecimal arithmetics, see output behind.

Test
0
0
0

Can anyone help me out?

Bhesh Gurung
  • 50,430
  • 22
  • 93
  • 142
Sergio del Amo
  • 76,835
  • 68
  • 152
  • 179

12 Answers12

311

The BigDecimal is immutable so you need to do this:

BigDecimal result = test.add(new BigDecimal(30));
System.out.println(result);
Bhesh Gurung
  • 50,430
  • 22
  • 93
  • 142
Vincent Ramdhanie
  • 102,349
  • 23
  • 137
  • 192
  • 29
    I can understand the confusion. Even though it's stated that BigDecimal is immutable, the documentation could be better. For example, the docs state for method `add(..)`: "augend - value to be added **to this** BigDecimal.". Furthermore, saying "... returns a **new** BigDecimal ..." instead of "... returns a BigDecimal ..." would be a nice touch. Perhaps I'm just nitpicking, but IMHO there's room for improvement here :-) – pauluss86 Jan 16 '14 at 17:08
  • 3
    Just a side note, BigDecimal is not completly immutable as its not final like String... – Zai Sep 17 '14 at 09:52
  • @Zai But that's just an implementation bug, not by design. Maintainable code should not exploit that. – C. K. Young Mar 25 '15 at 15:56
  • 1
    and why does Java implementation is a bit strange?! many other languages simply use + between numeric data types – sepehr Aug 06 '16 at 07:59
  • To answer @sepehr, because Java only offers operators for native types, not Objects. Java has no operator overloading ability. It would have been nice to have an add method with multiple values, but that's easily enough to achieve with a static method in a utility class. – David Bradley Mar 23 '22 at 22:01
39

It looks like from the Java docs here that add returns a new BigDecimal:

BigDecimal test = new BigDecimal(0);
System.out.println(test);
test = test.add(new BigDecimal(30));
System.out.println(test);
test = test.add(new BigDecimal(45));
System.out.println(test);
Ankur Goel
  • 1,075
  • 9
  • 10
18
BigDecimal test = new BigDecimal(0);
System.out.println(test);
test = test.add(new BigDecimal(30));
System.out.println(test);
test = test.add(new BigDecimal(45));
System.out.println(test);
Maurice Perry
  • 32,610
  • 9
  • 70
  • 97
10

BigInteger is immutable, you need to do this,

  BigInteger sum = test.add(new BigInteger(30));  
  System.out.println(sum);
ZZ Coder
  • 74,484
  • 29
  • 137
  • 169
10

It's actually rather easy. Just do this:

BigDecimal test = new BigDecimal(0);
System.out.println(test);
test = test.add(new BigDecimal(30));
System.out.println(test);
test = test.add(new BigDecimal(45));
System.out.println(test);

See also: BigDecimal#add(java.math.BigDecimal)

Bhesh Gurung
  • 50,430
  • 22
  • 93
  • 142
nfechner
  • 17,295
  • 7
  • 45
  • 64
  • 1
    Interesting that your answer is identical to Maurice Perry's. If you wanted to add the link, you should've just edited his. – forresthopkinsa Dec 12 '16 at 21:41
  • 1
    Actually, I didn't copy it but I think we both wrote the same answer at the same time (it is simply the fix for the given code anyway). I just took a minute longer for looking up the correct link. – nfechner May 09 '17 at 14:13
4

BigInteger is immutable, just like Strings. That means we cannot change it's content once the object is created, but we can re-assign it.

 BigInteger sum = test.add(new BigInteger(30));  
 System.out.println(sum);

.add() will return a new Object

4
//you can do in this way...as BigDecimal is immutable so cant set values except in constructor

BigDecimal test = BigDecimal.ZERO;
BigDecimal result = test.add(new BigDecimal(30));
System.out.println(result);

result would be 30
MAK
  • 575
  • 1
  • 10
  • 23
3
BigDecimal no = new BigDecimal(10); //you can add like this also
no = no.add(new BigDecimal(10));
System.out.println(no);

20

Yatish
  • 521
  • 3
  • 14
3

You can also do it like this:

BigDecimal A = new BigDecimal("10000000000");
BigDecimal B = new BigDecimal("20000000000");
BigDecimal C = new BigDecimal("30000000000");
BigDecimal resultSum = (A).add(B).add(C);
System.out.println("A+B+C= " + resultSum);

Prints:

A+B+C= 60000000000

t j
  • 7,026
  • 12
  • 46
  • 66
1

Using Java8 lambdas

List<BigDecimal> items = Arrays.asList(a, b, c, .....);

items.stream().filter(Objects::nonNull).reduce(BigDecimal.ZERO, BigDecimal::add);

This covers cases where the some or all of the objects in the list is null.

DaithiG
  • 849
  • 1
  • 9
  • 15
0
BigDecimal demo = new BigDecimal(15);

It is immutable beacuse it internally store you input i.e (15) as final private final BigInteger intVal; and same concept use at the time of string creation every input finally store in private final char value[];.So there is no implmented bug.

snipersnack
  • 133
  • 1
  • 1
  • 9
0

Just another example to add BigDecimals. Key point is that they are immutable and they can be initialized only in the constructor. Here is the code:

import java.util.*;
import java.math.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc;
        boolean first_right_number = false;
        BigDecimal initBigDecimal = BigDecimal.ZERO;
        BigDecimal add1 = BigDecimal.ZERO;
        BigDecimal add2 = BigDecimal.ZERO;

        while (!first_right_number)
        {
            System.out.print("Enter a first single numeric value: ");
            sc = new Scanner(System.in);
            if (sc.hasNextBigDecimal()) 
            {
                first_right_number = true;
                add1 = sc.nextBigDecimal();
            }
        }

        boolean second_right_number = false;
        while (!second_right_number)
        {
            System.out.print("Enter a second single numeric value: ");
            sc = new Scanner(System.in);
            if (sc.hasNextBigDecimal()) 
            {
                second_right_number = true;
                add2 = sc.nextBigDecimal();
            }
        }
        BigDecimal result = initBigDecimal.add(add1).add(add2);
        System.out.println("Sum of the 2 numbers is: " + result.toString());
    }
}
MultiplyByZer0
  • 6,302
  • 3
  • 32
  • 48