Java程序的输出|集合10(垃圾收集)

先决条件—— Java中的垃圾收集

null

难度等级: 中间的 在Java中,对象销毁由 垃圾收集器 模块和没有任何引用的对象都有资格进行垃圾收集。下面是一些关于垃圾收集的重要输出问题。 预测以下Java程序的输出:

  • 项目1:

    public class Test
    {
    public static void main(String[] args) throws InterruptedException
    {
    String str = new String( "GeeksForGeeks" );
    // making str eligible for gc
    str = null ;
    // calling garbage collector
    System.gc();
    // waiting for gc to complete
    Thread.sleep( 1000 );
    System.out.println( "end of main" );
    }
    @Override
    protected void finalize()
    {
    System.out.println( "finalize method called" );
    }
    }

    
    

    输出:

    end of main
    

    说明: 我们知道 定稿 方法在销毁对象之前由垃圾收集器调用。但在这里,诀窍在于str是字符串类对象,而不是测试类。因此,String类的finalize()方法(如果在String类中被重写)在str上被调用。如果一个类没有重写finalize方法,则默认情况下调用Object class finalize()方法。

  • 项目2:

    public class Test
    {
    public static void main(String[] args) throws InterruptedException
    {
    Test t = new Test();
    // making t eligible for garbage collection
    t = null ;
    // calling garbage collector
    System.gc();
    // waiting for gc to complete
    Thread.sleep( 1000 );
    System.out.println( "end main" );
    }
    @Override
    protected void finalize()
    {
    System.out.println( "finalize method called" );
    System.out.println( 10 / 0 );
    }
    }

    
    

    输出:

    finalize method called
    end main
    

    说明: 当垃圾收集器对对象调用finalize()方法时,它 忽视 方法和程序中引发的所有异常都将正常终止。

  • 方案3:

    public class Test
    {
    static Test t ;
    static int count = 0 ;
    public static void main(String[] args) throws InterruptedException
    {
    Test t1 = new Test();
    // making t1 eligible for garbage collection
    t1 = null ; // line 12
    // calling garbage collector
    System.gc(); // line 15
    // waiting for gc to complete
    Thread.sleep( 1000 );
    // making t eligible for garbage collection,
    t = null ; // line 21
    // calling garbage collector
    System.gc(); // line 24
    // waiting for gc to complete
    Thread.sleep( 1000 );
    System.out.println( "finalize method called " +count+ " times" );
    }
    @Override
    protected void finalize()
    {
    count++;
    t = this ; // line 38
    }
    }

    
    

    输出:

    finalize method called 1 times
    

    说明: 执行第12行后,t1有资格进行垃圾收集。所以,当我们在第15行调用垃圾收集器时,垃圾收集器将在销毁t1之前在t1上调用finalize()方法。但是在finalize方法中,在第38行中,我们再次通过t引用同一个对象,所以在执行第38行之后, 对象不再符合垃圾收集的条件。因此,垃圾收集器不会破坏对象。

    现在,在第21行中,我们再次使同一个对象符合垃圾收集的条件。在这里,我们必须澄清关于垃圾收集器的一个事实,即它将准确地对特定对象调用finalize()方法 时间因为在这个对象上,finalize()方法已经被调用,所以现在垃圾收集器将销毁它,而不再调用finalize()方法。

  • 方案4:

    public class Test
    {
    public static void main(String[] args)
    {
    // How many objects are eligible for
    // garbage collection after this line?
    m1(); // Line 5
    }
    static void m1()
    {
    Test t1 = new Test();
    Test t2 = new Test();
    }
    }

    
    

    问题: 执行第5行后,有多少对象符合垃圾收集条件? 答复:

    2
    

    说明: 由于t1和t2是m1()方法的本地对象,所以在方法完全执行后,除非返回其中任何一个,否则它们就有资格进行垃圾收集。

  • 方案5:

    public class Test
    {
    public static void main(String [] args)
    {
    Test t1 = new Test();
    Test t2 = m1(t1); // line 6
    Test t3 = new Test();
    t2 = t3; // line 8
    }
    static Test m1(Test temp)
    {
    temp = new Test();
    return temp;
    }
    }

    
    

    问题: 执行第8行后,有多少对象符合垃圾收集条件? 答复:

    1
    

    说明: 到执行第8行时,唯一没有引用的对象是生成的对象,即第6行的结果。记住“ Java严格按值传递 “因此,参考变量t1不受m1()方法的影响。我们可以使用finalize()方法检查它。finalize()方法中的语句“System.out.println(this.hashcode())”打印调用finalize()方法的对象hashcode值,然后将该值与在main方法中创建的其他对象hashcode值进行比较。

本文由 高拉夫·米格拉尼 .如果你喜欢GeekSforgek,并想贡献自己的力量,你也可以使用 写极客。组织 或者把你的文章寄去评论-team@geeksforgeeks.org.看到你的文章出现在Geeksforgeks主页上,并帮助其他极客。

如果您发现任何不正确的地方,或者您想分享有关上述主题的更多信息,请写下评论。

© 版权声明
THE END
喜欢就支持一下吧
点赞5 分享