Java的垃圾回收和空引用(java garbage collection and null ref

2019-07-02 19:23发布

在我的OCJP学习,我碰到以下问题:

class CardBoard {
           Short story = 200;
           CardBoard go(CardBoard cb) {
                cb = null;
                return cb;
           }
           public static void main(String[] args) {
             CardBoard c1 = new CardBoard();
             CardBoard c2 = new CardBoard();
             CardBoard c3 = c1.go(c2);
             c1 = null;
            // do Stuff 
}}

//达到doStuff时,有多少个对象资格GC?
正确答案是2,这意味着c1story的对象。

当达到行// doStuff,C3也为空。 为什么不是符合GC吗?

Answer 1:

C3是本地手柄,空引用,它并不指向(和赫弗指出)已分配对象。 因此没有什么GC。



Answer 2:

c3是不是对象。 这是一个变量引用无效。 变量可以没有资格GC。 只有对象资格GC。

资格GC的对象是其最初被引用的纸板c1 ,短实例最初由纸板引用最初引用的c1



Answer 3:

对于存储器中的对象的垃圾收集器的扫描,并且当它找到一个检查指向它(而不是反之亦然)当垃圾收集器调用的对象(内部存储器),其具有无柄指向它们被从内存中删除句柄。 在这种情况下的代码,你只需要在内存中创建2个对象不过三个把手。 垃圾收集器将只删除在最大2个对象(因为只有两个对象存在)C3仅在零位指向。 C1,C2,C3不会被删除。 他们用来指向的对象(在他们的情况下,没有其他的手柄点)将被删除。 所以在这一点,因为C3从未指出,在内存中的对象将其设置为空不会使垃圾收集器的差异。

希望我是有帮助



Answer 4:

你的CardBoard#go()方法不起作用。 它接收参考一些对象,立即忘记它,通过更换null ,并返回此null值。

因此,行

CardBoard c3 = c1.go(c2);

也什么都不做,即没有创建对象。 只是空分配到c3 。 因此,这不是因为收集已不存在,那么垃圾。



Answer 5:

所述C3本身只是一个参考变量 ,它是不是在堆空间 (即,不是在垃圾收集的范围)

CardBoard c3 = c1.go(c2); 只设置C3引用设置为null因此C3垃圾回收并没有影响,因为它不会使任何对象资格。



Answer 6:

C3拥有一个对象的引用,它只是做一些混乱。

我们已经创建了两个对象C1和C2,我们错过了为short类型的包装对象,所以基本上我们共创建了四个对象。

当我们正在C1 = null,则意味着,我们使用C1访问短对象可用于GC,而不是短对象,我们可以访问使用C2。

这可以使用下面的代码进行验证:

公共类纸板{

Short story = 200;

CardBoard go(CardBoard cb) {
    cb = null;
    return cb;
}

public static void main(String[] args) {
    Runtime run = Runtime.getRuntime();

    CardBoard c1 = new CardBoard();
    CardBoard c2 = new CardBoard();
    CardBoard c3 = c1.go(c2);

    // System.out.println(run.freeMemory());

    run.gc();
    // System.out.println(run.freeMemory());

    c1.story = 100;

    System.out.println(c1.story);
    c1 = null;
    run.gc();

    System.out.println(c2.story);

}

}

输出:100 200

这意味着,我们可以从C1访问c1和短篇小说是可进行垃圾回收没有c2的短篇小说。



文章来源: java garbage collection and null reference