Volatile
2015-07-16 09:42
176 查看
int a = 10;
int c = a;
理论上来讲每次使用a的时候都应该从a的地址来读取变量值,但是这存在一个效率问题,就是每次使用a都要去内存中取变量值,然后再通过系统总线传到CPU处理,这样开销会很大。所以那些编译器优化者故作聪明,把a读进CPU的cache里,像上面的代码,假如a在赋值期间没有被改变,就直接从CPU的cache里取a的副本来进行赋值。但是bug也显而易见,可能a已经被另一个线程改变而重新写回了内存,但这个线程并不知道,依旧按照原来的计划从CPU的cache里读a的副本进来赋值给c,结果不幸发生了。于是编译器的开发者为了补救这一bug,提供了一个Volatile让开发人员为他们的过失埋单,或者说提供给开发人员了一个选择效率的权利。当变量加上了Volatile时,编译器就老老实实的每次都从内存中读取这个变量值,否则就还按照优化的方案从cache里读。
当要访问的变量已在synchronized代码块中,或者为常量时,没必要使用volatile;
int c = a;
理论上来讲每次使用a的时候都应该从a的地址来读取变量值,但是这存在一个效率问题,就是每次使用a都要去内存中取变量值,然后再通过系统总线传到CPU处理,这样开销会很大。所以那些编译器优化者故作聪明,把a读进CPU的cache里,像上面的代码,假如a在赋值期间没有被改变,就直接从CPU的cache里取a的副本来进行赋值。但是bug也显而易见,可能a已经被另一个线程改变而重新写回了内存,但这个线程并不知道,依旧按照原来的计划从CPU的cache里读a的副本进来赋值给c,结果不幸发生了。于是编译器的开发者为了补救这一bug,提供了一个Volatile让开发人员为他们的过失埋单,或者说提供给开发人员了一个选择效率的权利。当变量加上了Volatile时,编译器就老老实实的每次都从内存中读取这个变量值,否则就还按照优化的方案从cache里读。
当要访问的变量已在synchronized代码块中,或者为常量时,没必要使用volatile;
相关文章推荐
- RB树
- 【c++】【vector】
- 【java并发】juc高级锁机制探讨
- 用Redis作为Mysql数据库的缓存(二)
- JAVA NIO 中的 zerocopy 技术提高IO性能
- 【MyBatis框架】SqlMapConfigl配置文件之常用的setting设置
- vsftpd移植到arm问题
- 数据结构基础 之 二叉堆实现堆排序
- eclipse中在线安装FindBugs
- TEA和QQTEA
- asp.net 常用知识点汇总整理
- 机器学习和统计模型的差异
- C++四种强制转换
- Step into Kotlin - 14 - 继承
- Ubuntu下Hello World驱动实现全过程
- 关于没有开启mbstring,mb_substr() 用不了的问题
- 用Redis作为Mysql数据库的缓存(-)
- 浅谈HTML5单页面架构(三)—— 回归本真:自定义路由 + requirejs + zepto + underscore
- hdu2602 — Bone Collector
- An analysis of the importance of the long tail in search engine marketing