3

I've got the following code to test:

import java.math.BigInteger;
import java.util.Random;

public class TestBigInteger {

    public static void main(String[] args) {
        BigInteger bigInteger = BigInteger.probablePrime(32, new Random())
                .multiply(BigInteger.probablePrime(32, new Random()));
        BigInteger n = BigInteger.probablePrime(20, new Random());
        while (!Thread.interrupted()) {
            bigInteger.mod(n);
        }

    }
}

And I've got the following plot from jconsole:

enter image description here

Why is that happening? Why mod operation takes really a lot of memory, if my bigInteger is only 64 bit length?

Peter Lawrey
  • 525,659
  • 79
  • 751
  • 1,130
Tony
  • 3,605
  • 14
  • 52
  • 84
  • Because the garbage collector doesn't run after every object, it runs when the memory reaches a certain threshold, and then cleans up all old references – Ferrybig Apr 13 '16 at 08:41
  • Well, it's creating garbage. `BigInteger.mod()` creates several objects which you're just throwing away. However you can see the GC getting the garbage every once in a while. – Kayaman Apr 13 '16 at 08:42
  • 1
    Why you say BigInteger is 8 byte? As object, it has at least 12 bytes of header plus information. I don't know internal structure of BigInteger, but I think it's far more than 8 byte of information. Also, object are lined up to multiple of 8.. so.. really can't be 64 bit – Jack Apr 13 '16 at 09:01
  • @Jack, I meant bigInteger is production of two 32 bit numbers. So I supposed bigInteger is 64 bit. – Tony Apr 13 '16 at 09:03

2 Answers2

7

This is not retaining a lot of memory, rather it is generating a lot of garbage.

    while (!Thread.interrupted()) {
        bigInteger.mod(n); // create a new objects each time.
    }

This loop creates garbage as fast as it can (with a bit of CPU work as well) As such you should expect to see the memory usage to be very active.

Why mod operation takes really a lot of memory, if my bigInteger is only 64 bit length?

This makes the memory usage higher because the actual amount of CPU spend doing the calculation is relatively small. If you had a bigger number, it would spend more time using the CPU compared to creating objects. As it is it spends more time creating garbage compared to the CPU it uses.

BTW I suggest you use VisualVM from Java 6 and Java Mission Control from Java 7, rather than jconsole.

Peter Lawrey
  • 525,659
  • 79
  • 751
  • 1,130
3

Function BigInteger.mod is using BigInteger.remainder function which is creating few of MutableBigInteger objects.

And you are creating a lot of objects by calling:

 while (!Thread.interrupted()) {
        bigInteger.mod(n); // create a new large object each time.
 }
Rudy Velthuis
  • 28,387
  • 5
  • 46
  • 94
user987339
  • 10,519
  • 8
  • 40
  • 45