Volatile boolean vs AtomicBoolean(易失性布尔值与原子布尔值)
问题描述
AtomicBoolean 做了哪些 volatile boolean 无法实现的功能?
What does AtomicBoolean do that a volatile boolean cannot achieve?
推荐答案
它们完全不同.考虑这个 volatile 整数的例子:
They are just totally different. Consider this example of a volatile integer:
volatile int i = 0;
void incIBy5() {
i += 5;
}
如果两个线程同时调用该函数,则 i 之后可能为 5,因为编译后的代码将与此有些相似(除了您无法在 int 上同步):
If two threads call the function concurrently, i might be 5 afterwards, since the compiled code will be somewhat similar to this (except you cannot synchronize on int):
void incIBy5() {
int temp;
synchronized(i) { temp = i }
synchronized(i) { i = temp + 5 }
}
如果一个变量是 volatile 的,对它的每个原子访问都是同步的,但实际上什么是原子访问并不总是很明显.使用 Atomic* 对象,可以保证每个方法都是原子的".
If a variable is volatile, every atomic access to it is synchronized, but it is not always obvious what actually qualifies as an atomic access. With an Atomic* object, it is guaranteed that every method is "atomic".
因此,如果您使用 AtomicInteger 和 getAndAdd(int delta),则可以确定结果将是 10.同样,如果两个线程同时否定一个 boolean 变量,使用 AtomicBoolean 您可以确保它之后具有原始值,使用 volatile boolean,你不能.
Thus, if you use an AtomicInteger and getAndAdd(int delta), you can be sure that the result will be 10. In the same way, if two threads both negate a boolean variable concurrently, with an AtomicBoolean you can be sure it has the original value afterwards, with a volatile boolean, you can't.
因此,当您有多个线程修改一个字段时,您需要使其成为原子或使用显式同步.
So whenever you have more than one thread modifying a field, you need to make it atomic or use explicit synchronization.
volatile 的目的是不同的.考虑这个例子
The purpose of volatile is a different one. Consider this example
volatile boolean stop = false;
void loop() {
while (!stop) { ... }
}
void stop() { stop = true; }
如果你有一个线程在运行 loop() 并且另一个线程在调用 stop(),如果你省略 volatile,因为第一个线程可能会缓存 stop 的值.在这里,volatile 提示编译器在优化时要更加小心.
If you have a thread running loop() and another thread calling stop(), you might run into an infinite loop if you omit volatile, since the first thread might cache the value of stop. Here, the volatile serves as a hint to the compiler to be a bit more careful with optimizations.
这篇关于易失性布尔值与原子布尔值的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!
本文标题为:易失性布尔值与原子布尔值
- Spring Boot连接到使用仲裁器运行的MongoDB副本集 2022-01-01
- 从 finally 块返回时 Java 的奇怪行为 2022-01-01
- value & 是什么意思?0xff 在 Java 中做什么? 2022-01-01
- Safepoint+stats 日志,输出 JDK12 中没有 vmop 操作 2022-01-01
- 将log4j 1.2配置转换为log4j 2配置 2022-01-01
- Eclipse 插件更新错误日志在哪里? 2022-01-01
- Jersey REST 客户端:发布多部分数据 2022-01-01
- 如何使用WebFilter实现授权头检查 2022-01-01
- Java包名称中单词分隔符的约定是什么? 2022-01-01
- C++ 和 Java 进程之间的共享内存 2022-01-01
