Finalization
suggest changeA Java object may declare a finalize
method. This method is called just before Java releases the memory for the object. It will typically look like this:
public class MyClass {
//Methods for the class
@Override
protected void finalize() throws Throwable {
// Cleanup code
}
}
However, there some important caveats on the behavior of Java finalization.
- Java makes no guarantees about when a
finalize()
method will called. - Java does not even guarantee that a
finalize()
method will be called some time during the running application’s lifetime. - The only thing that is guaranteed is that the method will be called before the object is deleted … if the object is deleted.
The caveats above mean that it is a bad idea to rely on the finalize
method to perform cleanup (or other) actions that must be performed in a timely fashion. Over reliance on finalization can lead to storage leaks, memory leaks and other problems.
In short, there are very few situation where finalization is actually a good solution.
Finalizers only run once
Normally, an object is deleted after it has been finalized. However, this doesn’t happen all of the time. Consider the following example1:
public class CaptainJack {
public static CaptainJack notDeadYet = null;
protected void finalize() {
// Resurrection!
notDeadYet = this;
}
}
When an instance of CaptainJack
becomes unreachable and the garbage collector attempts to reclaim it, the finalize()
method will assign a reference to the instance to the notDeadYet
variable. That will make the instance reachable once more, and the garbage collector won’t delete it.
Question: Is Captain Jack immortal?
Answer: No.
The catch is the JVM will only run a finalizer on an object once in its lifetime. If you assign null
to notDeadYet
causing a resurected instance to be unreachable once more, the garbage collector won’t call finalize()
on the object.
1 - See https://en.wikipedia.org/wiki/Jack_Harkness.