JLS第17.5.3段(最终字段的后续修改)经常使用术语最终字段安全上下文.虽然,从规范中可以理解(如果我在这里错了,请纠正我)
An implementation may provide a way to execute a block of code
in a final-fieldsafe context.
Run Code Online (Sandbox Code Playgroud)
确切的行为取决于实现,仍然没有明确的术语定义.
我可以假设,如果我们有一个最终字段冻结F(一个发生在对象构造的末尾或通过反射API设置的最终字段)和一个动作A,那么发生在之前(F,A ),那么A是在最终现场安全的背景下?
要通过"最终字段安全上下文" 帮助理解JLS 17.5.3的含义,请考虑以下代码
public static final AccountType SINGLETON_ACCOUNT_TYPE = new AwesomeAccountType();
Run Code Online (Sandbox Code Playgroud)
Java 5中之前,Java的有"功能",其中AwesomeAccountType及其分配SINGLETON_ACCOUNT_TYPE建设的线程安全是采取开发人员是安全的.不幸的是,规范是模糊的和/或没有说明行为,这导致不同的JVM实现具有不同的行为.结果是Java在这种情况下通常不是线程安全和可移植的.
这样做的原因是,构造AwesomeAccountType所涉及的操作的顺序可以在运行时重新排序,使得在完全构造对象之前对对象的引用可以对另一个线程可见.该行为是不确定的,它总是工作在单核CPU,通常对英特尔CPU的工作,但将下降匆忙上用较弱的存储模型的CPU如的DEC Alpha.
然后,"最终字段安全上下文"是分配给上述最终字段(SINGLETON_ACCOUNT_TYPE)的代码区域,它涵盖了AwesomeAccountType的所有构造函数以及JVM内部用于分配和初始化的代码.对象的内存.
Java内存模型的这些更改是在JSR133下进行的,以下FAQ对于理解所做更改的上下文非常有用:JSR133 FAQ.