Java threads and garbage collector [duplicate] Java threads and garbage collector [duplicate] multithreading multithreading

Java threads and garbage collector [duplicate]


  1. Any object which is referenced by an active thread may not be de-allocated.
  2. Yes, instances will be removed by the GC after the thread in `run()' ends.
  3. No prob.


  1. Could those instances be removed by the garbage collector before the thread in run() ends? (In other words: is there any reference to the Foo objects?)

No. While the constructor is running GC won't collect the object. Otherwise even the simplest:

Customer c = new Customer();

could fail while the constructor of Customer is running. On the other hand when you start a new thread, the thread object becomes a new GC root, so everything referenced by that object is not a subject to garbage collection.

  1. And, in the other hand, will those instances be removed by the GC after the thread in `run()' ends, or are we wasting memory ("memory leak")?

Once the thread is done, it is no longer a GC root. If no other code points to that thread object, it will be garbage collected.

  1. If either 1. or 2. are a problem, what's the right way to do it?

Your code is just fine. However:

  • starting a new thread in a constructor is a poor idea from unit-testing point of view

  • keeping a reference to all running thread might be beneficial if e.g. you want to interrupt these threads later.


Starting a new thread without specifying a thread group will add it to the default group:

If group is null and there is a security manager, the group is determined by the security manager's getThreadGroup method. If group is null and there is not a security manager, or the security manager's getThreadGroup method returns null, the group is set to be the same ThreadGroup as the thread that is creating the new thread.

The group will keep a reference to the thread as long as it is alive, so it can't be GC'd during that time.

When a thread terminates (= when run() returns for whatever reason), the thread is removed from the thread group. This happens in the private method exit() which is called from native code. This is the point in time when the last reference to the thread is lost and it becomes eligible for GC.

Note that the code indicates that ThreadGroup can be null but that isn't the case. The various null-checks are just to avoid NPEs in the rare case that something goes wrong. In Thread.init(), you would get NPEs if Java couldn't determine a thread group.