我发现在很多地方,当垃圾回收器或System.gc()成功保留了冗余对象消耗的内存而没有更多引用时,将调用java中的finalize()方法。还发现该方法被调用不超过一次。我对Java并不陌生,但是经验也不多。我可能对此有误解,但让我们说一段代码
public class Solution {
@Override
protected void finalize(){
System.out.print("method called");
}
public static void main(String... args){
Solution obj1= new Solution();
Solution obj2 = new Solution();
Solution obj3 = new Solution();
System.gc();
obj1=obj2;
System.gc();
obj3=null;
System.gc();
}
}
在这里,finalize方法被调用两次,因为内存堆两次有资格进行垃圾清理。因此,对于我是否正确了解整个事情还是应该按照其行为方式进行操作,我有些困惑。
No. The
finalize()
method will only be called once by the GC on an object. The JVM sets a flag in the object header (I think) to say that it has been finalized, and won't finalize it again.The javadoc states this explicitly:
Of course, there is nothing an object method calling
this.finalize()
any number of times.Note that
finalize()
is deprecated in Java 9 and later for reasons stated in the javadoc. It is recommended that you switch to using one of the following instead:AutoCloseable
+ try with resourcesCleaner
PhantomReference
有人这样评论:
这有两个原因,这是不正确的。
The javadoc explicitly states that there are no guarantees that
finalize
will ever be called. The thing that is guaranteed is that it will be called (once) before an object's storage is reclaimed. That is a weaker statement than the statement that the comment makes.One scenario where garbage collected objects may not be finalized is if the JVM exits soon after a GC run.
In fact,
Object::finalize
is not overridden, the JVM will typically skip the finalization step.