假设你有这个代码片段
private final Set set = new HashSet() {{ add(1); }};
SomeConstructor() {
printSet();
}
long printSet() {
new Thread(() -> {System.out.println(set)}).start();
}
例如,如果编译器决定使其看起来像
private final Set set;
SomeConstructor() {
printSet();
set = new HashSet() {{ add(1); }};
}
这将是一个问题,因为calculateWaitTime()创建一个新线程,该线程可能会将集合视为null或其中没有1。
那么问题又来了,这种重新排序可能吗?或者,在构造函数外部初始化的所有最终字段是否在构造函数之前初始化,或者至少始终由编译器移动到构造函数的顶部
最佳答案
final
字段不可能。
17.5.2 Reading final Fields During Construction
A read of a final field of an object within the thread that constructs that object is ordered with respect to the initialization of that field within the constructor by the usual happens-before rules. If the read occurs after the field is set in the constructor, it sees the value the final field is assigned, otherwise it sees the default value.
但是您也可以看到,它不能保证使用反射进行后续的final
字段修改。请参阅17.5.3了解更多详情。
关于java - 在构造函数之外初始化的最终字段是否会在运行构造函数之前初始化?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48658540/