对象字段的完成
Finalization of object fields
我很难理解 Java SE 8 语言规范第 12.6.1 和 12.6.2 节的含义。我正在使用 Java 对象管理本机对等体的产品,因此正确完成(直到我们有机会重写引用队列)很重要。
很明显,从规范来看,终结器可能 运行 乱序。这是我遇到困难的可达性。
我相信规范是这样说的:
class A {
public Object o = new Object()
protected synchronized void finalize() throws Throwable { o = null; }
}
class B {
A a = new A()
protected void finalize() throws Throwable {
a.getClass() // always works: a cannot be null.
a.o.getClass() // might NPE: a's finalizer might have been run
}
}
class C {
A a = new A()
protected void finalize() throws Throwable {
synchronized (a) {
a.getClass() // always works: a cannot be null.
a.o.getClass() // always works: a.o cannot be null.
}
}
}
上面有4个断言。我非常感谢确认它们是真实的,或者解释为什么一个或多个是错误的。
如果A.finalize
先获取锁,那么a.o.getClass()
即使在C
中也会NPE。最后的断言是错误的。
在 可达性方面 可以这样想:假设 A
和 C
是循环可达的,那么它们将在“相同的时间”达到不可达性时间”。因此,A
必须在 C
.
之前完成是不合理的
我猜 直接 修复可能是 A
的引用计数。但是,靠GC来清理非内存资源也不会好到哪里去。
我很难理解 Java SE 8 语言规范第 12.6.1 和 12.6.2 节的含义。我正在使用 Java 对象管理本机对等体的产品,因此正确完成(直到我们有机会重写引用队列)很重要。
很明显,从规范来看,终结器可能 运行 乱序。这是我遇到困难的可达性。
我相信规范是这样说的:
class A {
public Object o = new Object()
protected synchronized void finalize() throws Throwable { o = null; }
}
class B {
A a = new A()
protected void finalize() throws Throwable {
a.getClass() // always works: a cannot be null.
a.o.getClass() // might NPE: a's finalizer might have been run
}
}
class C {
A a = new A()
protected void finalize() throws Throwable {
synchronized (a) {
a.getClass() // always works: a cannot be null.
a.o.getClass() // always works: a.o cannot be null.
}
}
}
上面有4个断言。我非常感谢确认它们是真实的,或者解释为什么一个或多个是错误的。
如果A.finalize
先获取锁,那么a.o.getClass()
即使在C
中也会NPE。最后的断言是错误的。
在 可达性方面 可以这样想:假设 A
和 C
是循环可达的,那么它们将在“相同的时间”达到不可达性时间”。因此,A
必须在 C
.
我猜 直接 修复可能是 A
的引用计数。但是,靠GC来清理非内存资源也不会好到哪里去。