6

Oracle 关于原子访问的文档(位于http://docs.oracle.com/javase/tutorial/essential/concurrency/atomic.html)说:

“一个volatile变量建立了happens-before关系......这意味着......当一个线程读取一个volatile变量时,它不仅会看到对volatile的最新更改,还会看到导致代码的副作用改变。”

我很难解决这个问题。我了解 volatile 变量是如何工作的(在 >= Java 5 中),但我想知道 java 如何决定什么副作用“导致”了 volatile 变量的变化。

所以我想我的问题是:这个保证有什么副作用?

编辑:

所以我了解到,如果线程 A 修改了一个 volatile 变量,然后线程 B 读取它,那么在写入 volatile 变量之前发生的线程 A 的所有写入相对于线程 B(即缓存的值)都是“一致的”受线程 A 上述写入影响的变量在线程 B) 中无效。如我错了请纠正我。

4

2 回答 2

5

大多数多处理器缓存具有一致性机制,因此惩罚并不像刷新所有缓存那么糟糕。

在这样做之前写入 volatile 的线程中的任何写入都将被读取 volatile 之后的线程看到。

于 2012-02-07T00:24:21.867 回答
3

双重检查锁定为例。当你创建一个对象时,很多事情都会在幕后发生:

MyClass c=new MyClass();

分配内存,调用构造函数,并将内存位置分配给变量 c。JVM 可以重新排序这些操作。如果分配了内存,分配了值,并且线程在调用构造函数之前中断并使用该值,则会导致问题。

volatile MyClass c=new MyClass();

根据 1.5 规则,分配保证是这些事件中的最后一个。“副作用”是分配和构造函数调用。

于 2012-02-07T00:28:58.457 回答