Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/328.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
我应该在java中使用finalize()还是不使用?_Java - Fatal编程技术网

我应该在java中使用finalize()还是不使用?

我应该在java中使用finalize()还是不使用?,java,Java,为什么Java中根本不保证执行finalize()?是否不应使用finalize()方法 考虑下面的程序 class Test{ protected void finalize() { System.out.println("Will i execute?"); } public static void main(String args[]) { Test t=new Test(); } } 此程序运行时有一个空输出。我们知道

为什么Java中根本不保证执行
finalize()
?是否不应使用
finalize()
方法

考虑下面的程序

class Test{
   protected void finalize()
   {
       System.out.println("Will i execute?");
   }
   public static void main(String args[])
   {
         Test t=new Test();
   }
}
此程序运行时有一个空输出。我们知道,
finalize()
用于在对象符合垃圾收集条件之前清理任何外部资源&
finalize()
将由JVM调用。在
finalize()
中,我们将指定在销毁对象之前必须执行的操作。
finalize()
method邪恶吗

finalize()
在垃圾回收确定不再有对对象的引用时,由垃圾回收器对该对象调用

您可以使用
System.gc()
显式调用垃圾收集,并检查语句是否打印出来。 但是JVM有权忽略您的请求(实际上取决于JVM实现)。只有当JVM的内部状态告诉它有太多垃圾需要收集时,它才会运行GC(我将执行的行)并打印出来

,因为后面会有很多引号

我们知道finalize()用于在对象符合垃圾收集条件之前清理任何外部资源

否。一旦对象符合垃圾收集条件,则可以调用
finalize()
<理论上讲,code>finalize会使对象不再符合垃圾收集的条件,垃圾收集器会跳过它。如上所述

为对象调用finalize方法后,不再 直到Java虚拟机再次确定 不再有任何方法可以访问此对象 通过任何尚未死亡的线索

为什么在Java中不能保证finalize()的执行

它保证运行。正如Javadoc所述

finalize的总合同是,如果 JAVA™ 虚拟机已确定不再存在任何方法 任何尚未访问该对象的线程都可以通过它访问该对象 死亡,但因最终确定 准备完成的其他对象或类

不能保证的是何时或是否会发生垃圾收集

我应该在java中使用finalize()还是不使用


这取决于您的用例。从阅读javadoc开始,理解其中的含义。

如果我理解您的问题,您可以使用
System.gc()
请求垃圾收集,如下所示:

@Override
protected void finalize() {
  System.out.println("I will execute.");
}

public static void main(String args[]) {
  Test t = new Test();
  t = null;                     // <-- make it eligible for gc.
  System.gc();                  // <-- request gc.
  System.runFinalization();     // <-- run finalization(s).
  System.out.println("Exit");   // <-- exit.
}

在从内存中删除对象之前,垃圾收集线程调用该对象的finalize()方法,并提供执行任何类型清理操作的机会

通常,在以下情况下,对象可以在Java中进行垃圾收集:

  • 该对象的所有引用都显式设置为null,例如object=null
  • 对象在块内创建,一旦控件退出该块,引用将超出范围
  • 父对象设置为null,如果一个对象持有另一个对象的引用,并且当您将容器对象的引用设置为null时,子对象或包含的对象将自动符合垃圾收集的条件
  • 如果一个对象只有通过WeakHashMap的活动引用,它将有资格进行垃圾收集

    公共测试(){
    System.out.println(“创建的对象”);
    }
    受保护的void finalize(){
    System.out.println(“我会执行吗?”);
    }
    公共静态void main(字符串参数[]){
    测试=新测试();
    test=null;
    新测试();
    gc();
    }

  • jvm在将任何特定类的对象作为垃圾收集之前调用该类的finalize()

    下一个问题是什么时候类的对象被收集为垃圾? 答案是:

    当没有更多的对象引用该对象,或者没有更多的对象引用指向分配的内存空间,或者一个对象通过WeakHashMap只有活动引用时,它将有资格进行垃圾收集。

    < P>作为一个选项,我们可以使用Stase.gC.()或运行时.gc-()来给JVM一个考虑垃圾收集的请求。但jvm是否会监听或忽略您的请求取决于以下因素:

  • JVM的内部实现及其垃圾收集算法
  • Java堆大小
  • 堆中可用的可用内存

  • 首先,它不是邪恶的。其次,在GC回收对象之前调用finalize()。第三,您的对象不重,无法获得GC。第四,通常调用finalize()不是一个好主意。Joshua Block讨论了这些问题以及何时可以在这里使用Finalize()。LostMind和Hari有一个很好的答案。终结者不好,离他们远点。如果必须的话,试着找一个替代方法,比如s,但是最好的选择是什么都不做,只允许对象被垃圾收集。我会说使用
    Try{}finally{}
    来释放资源。通常不需要实现
    finalize
    。这不是一个精确的答案:
    finalize()
    是一个可以实现的方法,当VM确定无法访问您的对象时,它将被VM调用。这根本不是对虚拟机的建议。@ErwinBolwidt-Ya。。编辑:)谢谢。(对于错误的和误导性的陈述,很抱歉)+1。。基本上,当对象变得不可访问时,它就有资格进行GC。
    public static void main(String args[]) {
      Test t = new Test();
      t = null;                     // <-- make it eligible for gc.
      System.gc();                  // <-- request gc.
      // System.runFinalization();  // <-- run finalization(s).
      System.out.println("Exit");   // <-- exit.
    }