2

This is a question about garbage collection in java: if one allocates a large block of memory (using new int[BIG_NUMBER] or however), is there any guarantee that a garbage collector will collect the garbage before an OutOfMemoryError is thrown? Is this behaviour of garbage collector a part of the Java spec by now?

I have learnt that a garbage collector itself might throw such exception in case it takes too long to collect the garbage, at least in the case of Sun Hotspot Java Virtual Machine

«The parallel / concurrent collector will throw an OutOfMemoryError if too much time is being spent in garbage collection: if more than 98% of the total time is spent in garbage collection and less than 2% of the heap is recovered, an OutOfMemoryError will be thrown. This feature is designed to prevent applications from running for an extended period of time while making little or no progress because the heap is too small. If necessary, this feature can be disabled by adding the option -XX:-UseGCOverheadLimit to the command line. »

but this may be disabled, according to the citation, by adding an option to the command line.

Peter Lawrey
  • 525,659
  • 79
  • 751
  • 1,130
John Donn
  • 1,718
  • 2
  • 19
  • 45
  • *"is there any guarantee that a garbage collector will collect the garbage before an OutOfMemoryError is thrown?"* Certainly not if there is a reference to the block of memory. – Andrew Thompson Dec 13 '11 at 10:34
  • 1
    I did not phrase my question well: the question is what the JVM does when it tries to allocate a large block of memory, and seeing that the heap space left is insufficient: tries first to garbage collect, sees that the memory left after garbage collection is still insufficient and then raises OutOfMemoryError, or else, relying that garbage collector thread(s) does its job often enough, raises OutOfMemoryError immediately without trying to garbage collect first. It seems that Peter Lawrey below answered the question. – John Donn Dec 13 '11 at 10:58

2 Answers2

3

AFAIK, It has always been part of the Spec.

The early OutOfMemoryError if the VM is very low on memory is a Java 6 feature and was introduced to stop the VM when it becomes unusable but not quite dead.

I wouldn't turn this feature off, you are far better off engineering your system so you never get close to 98% memory usage. I would suggest 30% is a more comfortable level to run at.

From the Javadoc for Java 1.4.2 (introduced in 2002) http://docs.oracle.com/javase/1.4.2/docs/api/java/lang/OutOfMemoryError.html

Thrown when the Java Virtual Machine cannot allocate an object because it is out of memory, and no more memory could be made available by the garbage collector.

Peter Lawrey
  • 525,659
  • 79
  • 751
  • 1,130
-2

It is simple, no. Your program may call Runtime.gc() for help.

pinxue
  • 1,736
  • 12
  • 17
  • No, it will run before OutOfMemoryError, and gc() does not force the GC to run. – Sean Owen Dec 13 '11 at 10:30
  • While you are correct that System.gc() is just a suggestion, in practice all vm implementations that I am aware of does do a gc when the System.gc() is called. The disruptor guys does an explicit gc at off-hours to force a full gc when the consequences are small. – Erik Dec 13 '11 at 12:53