2

在 之后new A(),我们分配足够的内存来保存A包含的所有对象。

对象A()可能包含其他对象,例如B()C()

问题 1:什么时候A()不再需要并且你想从堆中删除它,设置它的引用来null解决问题吗?(如果不是,那么现在JVM向该GC对象发出信号的正确方法是什么?)

问题 2:如果是这样,指向B()和的实例会发生什么情况?C()

问题3:有没有办法可以观察到这种效果?(内存被释放以释放对象)

4

7 回答 7

5

将 A 设置为 null 会将 A 标记为要被 GC 释放的候选对象。如果对这些实例的唯一引用来自实例 A,则 B 和 C 的实例也将被标记。

编辑问题 3:调试此效果的一种简单方法是使用方法finalize;当一个对象被 GC'ed 时,他的finalize被调用。

但是,请注意这个方法:finalize 不能保证总是被执行(因为 GC 不能保证释放一个对象)并且不应该被用于应用程序的一般目的。

根据您的 IDE,有更好的调试工具。例如在eclipse中:http ://www.yourkit.com/docs/80/help/garbage_collection.jsp

于 2012-06-11T16:06:40.563 回答
3

如果您有实时参考BC那么它不会被 GCed

在任何时候,如果任何对象都没有对其的实时引用,则该对象已准备好进行 GC

class A{
 B b = new B();
 C c = new C();
}

现在当你做

A a = new A();
a= null;//instance referred by a,b & c are ready to be collected in this system
于 2012-06-11T16:04:19.950 回答
2

对象 A() 可能包含其他对象,例如 B() 和 C()

对象只包含原语和对其他对象的引用。

问题 1:当不再需要 A() 并且您想将其从堆中删除时,将其设置为 null 的引用是否有效?

很少需要,但您可以这样做。

问题 2:如果是这样,指向 B() 和 C() 的实例会发生什么情况

没什么,它们是不相关的对象。

问题3:有没有办法可以观察到这种效果?(内存被释放以释放对象)

您可以覆盖该finalize()方法或使用 ReferenceQueues。这只会通知您收集的对象而不是丢弃对象。最好避免需要这样做。


可以收集没有来自根上下文(例如线程堆栈)的强引用的对象。这无关紧要。设置对 null 的引用可以允许这种情况发生,但更常见的是,允许变量超出范围是丢弃对象的更简单方法。

如果您有对象 B 并且它指向指向 B 的 C 并且没有对这些对象的其他引用,即使有对这些对象的引用,它们仍将被清除。

于 2012-06-11T16:08:06.797 回答
1

您不能强制 GC 删除对象。GC 会自动删除任何可以安全删除的对象。您可以通过调用强制 GC 运行System.gc(),这将删除它可以删除的任何对象。

A = null仅当不存在对该对象的其他引用时才会删除该对象。

一般来说GC是存在的,所以你不必担心删除和内存收集。如果一个东西可以安全地删除,它最终会是。

B()如果停止指向它们并且是唯一指向它们的东西,C()则将被删除。AA

于 2012-06-11T16:06:00.400 回答
1
  1. 如果将其设置为 null,那么是的,它是一个信号,可以在GC需要内存时释放内存。但这只有在没有更多实例引用该对象时才会发生。

  2. 如果仍然有实例引用一个对象,则在完全没有引用该对象的实例之前,它不会被 GC-ed。所以 B() 和 C() 只有当 A() 是唯一引用它们的时候才会被 GC-ed。

  3. 通过使用 Java 使用 Scanner 读取一个巨大的文本文件(大约 3mb),然后关闭并丢弃 Scanner,并在完成后调用 System.gc(),可以很容易地观察到这种效果。

于 2012-06-11T16:07:56.467 回答
1

如果您取消对 A 的所有引用,并且如果没有其他对 B 和 C 的实时引用,那么当 GC 运行时,这些引用也将被 GC。

调用System.gc()并不能保证 gc 会立即运行。它可能会或可能不会运行,根本无法保证。

And There is no guaranteed way to force gc run immediately as you request it.

是的,您可以看到 gc 运行释放内存时的效果。

要查看有关堆/内存使用情况的可视化图形/信息...,您可以使用 jdk 工具,在以下位置找到适用于 Windows 的信息:

JAVA_HOME\bin\jconsole.exe 
于 2012-06-11T16:10:34.620 回答
1

它是规则的拇指,that when an object has NO reference attached to it, its a toast for the Garbage collector to eat.

将 A 标记为 null 将使 A 成为 GC 的祝酒词。如果指向 A 的引用是对 B 和 C 的唯一引用,那么这两个也是垃圾收集的候选对象

finalize 是对象类方法,当对象被垃圾回收时调用。

于 2012-06-11T16:57:27.023 回答