11

Possible Duplicate:
Forcing Garbage Collection in Java?

Can I Force Garbage Collection in Java by any means?

System.gc() is just a suggestion.It's useless.

When I know for sure that some resources won't be used any more,why can't I force to clean them?

Just like delete() in C++ and free() in C?

When there are lots of resources that can't be reused,this can really suck the performance.All that we can do is sleep().

Any solutions?Thanks

Community
  • 1
  • 1
Jacob
  • 619
  • 1
  • 5
  • 17

3 Answers3

14

Nope, System.gc() is as close as you can get. Java isn't C or C++, the JVM manages memory for you, so you don't have that kind of fine grained control. If you set objects you're no longer using to null, or loose all references, they will get cleaned up. And the GC is pretty smart, so it should take good care of you.

That said, if you are on a unix box, and force a thread dump (kill -3), it'll pretty much force garbage collection.

Michael
  • 6,141
  • 2
  • 20
  • 21
  • 5
    +1 for "The GC is smart." (It's _really_ smart, and it's very rarely the true cause of performance bottlenecks.) – Louis Wasserman Mar 02 '12 at 03:31
  • @Michael What is it about unix box and forcing a thread dump? How can this guarantee garbage collection? – Geek Jan 04 '14 at 07:53
  • 1
    @Geek - Whenever the JVM performs a thread dump, it pauses itself for a garbage collection. It'll do that on any OS to be honest, it's just easiest to do on unix/linux due to the availability of 'kill'. If you're on windows with cygwin, I believe you can accomplish the same thing. – Michael Jan 06 '14 at 03:27
6

You shouldn't be trying to force GC - if you are running low on memory then you have a memory leak somewhere. Forcing GC at that point won't help, because if you are holding a reference to the object then it still won't be garbage collected.

What you need to do is solve the real problem, and make sure you are not holding references to objects you are not using any more.

Some common culprits:

  • Holding lots of references in a large object graph that never get cleared up. Either set references to null when you don't need them any more, or better still simplify your object graph so it doesn't need all the extra long-term references.
  • Caching objects in a hashmap or something similar that grows huge over time. Stop doing this, or use something like Google's CacheBuilder to create a proper soft reference cache.
  • Using String.intern() excessively on large numbers of different strings over time.
  • References with larger scope than they need. Are you using an instance variable when it could be a local variable, for example?
mikera
  • 105,238
  • 25
  • 256
  • 415
  • Good suggestions.I will have a try.Thanks – Jacob Mar 02 '12 at 03:53
  • 2
    There are reasons to force a GC. Most obviously, if you're about to enter a latency sensitive piece of code that interacts with the real world, and would like to minimize the chance that the GC pauses for a "big" collection. Of course, if latency is really important, Java is unlikely to be the best language for the problem, but sometimes you're in a place where that kind of mistake can't be undone. – Jon Watte May 13 '16 at 23:40
  • I've just debugged an application when memory grew uncontrollably, without any apparent cause, and quickly ran out of 150GB. Adding System.gc() in strategic places fixed it and kept it under 35GB. The application is memory-intensive and highly parallel. GC isn't a magic bullet and is optimized for typical use cases. Sometimes it's necessary to give gc() hint even when all the references are released/out of scope. – morfizm Jul 06 '17 at 16:19
  • If you are using WeakReference in your code then there is a valid case for forcing garbage collection of specific objects in unit tests to check that your weak-reference logic is working when the object is gone. – flodin Apr 08 '20 at 08:52
1

There is no way to explicitly instruct the JVM to collect garbage. This is only performed when the system needs the resources.

The only two actions I'm aware of to potentially get the GC running are the following:

  1. As you stated, attempt to "suggest" that GC now would be a good time by called System.gc().
  2. Set any references you are not using to the null reference to make the elements eligible for collection.

On my second point, see the answer here: Garbage collector in java - set an object null. In essence, if you don't make the objects you don't need available for garbage collection (by losing the reference you have to it) then there is no reason for the garbage collector to run, because it's unaware of any available garbage.

In addition, it's important to consider why/how those objects in memory are affecting performance:

  • Are you getting lots of OutOfMemoryExceptions? This could be resolved by point #2 and by increasing the available heap space for the JVM.
  • Have you done measurements to see that more objects in the JVM's allocated heap space makes a difference in performance? Determining when you could let references to objects go earlier could help reduce these issues.
Community
  • 1
  • 1
pseudoramble
  • 2,541
  • 22
  • 28