请参阅以下代码,我只想做一些关于不安全的事情。
import sun.misc.Unsafe;
import java.lang.reflect.Field;
import java.util.*;
public class A {
public static void main(String[] args) throws Exception {
Field f = Unsafe.class.getDeclaredField("theUnsafe");
f.setAccessible(true);
Unsafe u = (Unsafe) f.get(null);
System.out.println("the while start at:" + new Date());
long total = 0;
while (true) {
u.allocateInstance(B.class);
total++;
if (total % 100000000 == 0) {
System.out.println(total);
System.gc();
}
}
}
}
class B {
private int a;
private int b;
private double d;
private float e;
@Override
protected void finalize() {
try {
super.finalize();
} catch (Throwable e) {
System.out.println("catch excep");
}
System.out.println("class B finalize, the a:" + a);
}
}
代码永远不会是oom,但是永远不会调用类B的终结。为什么? 我找不到关键信息。...
答案 0 :(得分:1)
This OpenJDK thread注意以下几点:
Unsafe.allocateInstance()通过直接调用JNI的
AllocObject()
函数[1]在HotSpot VM中实现。 在Java堆中分配了一个对象实例,但没有为该实例调用任何构造函数。
此外,Java Langauge Specification (§12.6.0)特别声明:
对象的构造函数的完成发生在(§17.4.5)的finalize方法执行之前(正式>形式)。
鉴于在您的代码中您从未实际调用分配的实例的构造函数,因此必须先违反上述happens-before order (§17.4.5)才能调用Object.finalize()
方法。
因此,将永远不会调用Object.finalize()
方法。