volatile作用
确保数据每次都从源头读取,即每次都从内存中读取,不从缓存中读取。
这样做的目的是确保不会被优化
int i = 0;
int main(int argc, char **argv)
{
const char *str;
if (i == 0) {
str = "hello";
} else {
str = "world";
}
return 0;
}
如上一段代码,从main中可以确定i一定等于0,所以在优化后就会直接让str = "hello";
但是其他线程可能会修改i的值,这样就会出错。加上volatile
这段比较代码就不会被优化
volatile为什么不等于原子操作
1、修改一个变量的值会经过以下三个步骤
- 从内存读取值 ( R )
- 在算术逻辑单元ALU进行计算 ( M )
- 将计算后的值写回内存 ( W )
两个线程都对加上volatile的整形变量x
累加,初始值为0
- p1读取到x的值
- p1对x进行累加
- p2读取x的值
- p1将x写回内存
- p2对x进行累加
- p2将x写回内存
最终结果x将会是1,显然是错误的
可以让p1读取前先锁定内存总线,在写完后释放内存总线,这样才算是原子操作,整个过程要么全部成功,要么全部失败。