我即将参加并发编程类(class)的考试。该类(class)的结构相当好,但我觉得我一定没有像我想的那样理解“volatile”关键字。我已经通读了其他关于它如何工作的帖子,这似乎是有道理的,但我对 Java 的整体理解限制了我。这些是练习题 T/F,有人介意回答它们并解释它们为什么是对或错吗?我已经把我最好的猜测和解释放在
一个。 ____多个线程共享一个 int 变量计数, 其中对 count 的唯一操作是读取其值并增加它。 将 count 标记为 volatile 就足够了。
false,volatile 关键字确保没有这个变量的本地缓存,但是竞争条件仍然会发生,因为新值依赖于先前的计数(因此操作不是原子的),所以两个线程可以读取值,增加它并且在写回时仍然存在竞争条件。如果计数不依赖于先前的值(例如仅写入的 ID 号),这将起作用。
____ 长变量计数在多个线程之间共享, count 上唯一的操作是读取它的值,并递增 它。将 count 标记为 volatile 就足够了。
与上面相同,除了即使该值不依赖于先前的值,这也不是线程安全的,因为它永远不是原子操作,因为 long 需要两个写周期来进行高 32 位写入和读取
____ boolean 变量 b,最初为 false,被共享 多个线程。一个特定的线程将其值设置为 true,另一个 线程读取值。将 b 标记为 volatile 就足够了。
是的,更改 boolean 值是原子的,可以在中断发生之前发生,并为所有其他线程更新。
____ boolean 变量 b 在多个线程之间共享。 任何线程都可以设置或读取它的值。一旦 b 被设置为 true,它仍然是 true 今后。将 b 标记为 volatile 就足够了。
没错,同上。
非常感谢!
最佳答案
一个。你的答案很好(即 volatile 是不够的)
“这绝不是原子操作,因为 long 需要两个写周期来进行高位和低位 32 位写入和读取” => 这对于非 volatile 变量来说太强了:非 volatile 长赋值可能会也可能不会是原子的。它在 64 位处理器上通常是原子的,但 Java 内存模型不提供任何保证。但是,volatile 长赋值保证是原子的。
你的回答很好(虽然我不明白你所说的“在中断发生之前”是什么意思)
你的回答很好
关于java - java 中的 volatile,具有 long、int、boolean 和许多不同的 write 情况,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22332279/