我遇到过以下说法:“读取或写入 volatile 变量会造成内存屏障,整个缓存将被刷新/失效。”
现在考虑以下执行场景:
初始 volatile boolean 屏障;
初始 int b = 0;
线程 1 b = 1;//write1
线程 1 barrier = true;//write2
线程 2 barrier = true;//write3
线程 2 print(b);//r1
问题:线程2保证打印1吗?
根据这个说法,我会回答是:线程 1 在 write2 上刷新其缓存(以便 b = 1
最终进入主内存),并且线程 2 在 write3 上使其缓存无效(因此它将从主内存读取 b
)。
但是,在相关JLS sections我无法找到这种行为的保证,因为 write3 是写入,而不是读取。因此,以下看似关键的条款并不适用:
A write to a volatile variable v (§8.3.1.4) synchronizes-with all subsequent reads of v by any thread (where "subsequent" is defined according to the synchronization order).
我是否遗漏了其他信息,或者我是否误解了某些内容?
(相关问题:
最佳答案
我认为,您在引用的短语中突出显示了一个错误的单词(我的意思是,它与读取同步的事实到目前为止并不是这里的主要问题):“对 volatile 变量 v (§8.3.1.4) 的写入与任何线程对 v 的所有后续读取同步”。
请注意,它根本没有提及其他变量的读取。据您所知,Thread-1 的 b
版本可能仍然存在于寄存器中。
关于java - 我们可以专门使用 volatile 写入来强制缓存一致性吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27933696/