作者:Doug lea 译者:杜建雄校对者:方腾飞

Volatile

从原子性,可见性和有序性的角度分析,声明为volatile字段的作用相当于一个类通过get/set同步方法保护普通字段,如下:

final class VFloat {

private float value;

final synchronized void set(float f) { value = f; }

final synchronized float get() { return value; }

}

与使用synchronized相比,声明一个volatile字段的区别在于没有涉及到锁操作。但特别的是对volatile字段进行“++”这样的读写操作不会被当做原子操作执行。

另外,有序性和可见性仅对volatile字段进行一次读取或更新操作起作用。声明一个引用变量为volatile,不能保证通过该引用变量访问到的非volatile变量的可见性。同理,声明一个数组变量为volatile不能确保数组内元素的可见性。volatile的特性不能在数组内传递,因为数组里的元素不能被声明为volatile。

由于没有涉及到锁操作,声明volatile字段很可能比使用同步的开销更低,至少不会更高。但如果在方法内频繁访问volatile字段,很可能导致更低的性能,这时还不如锁住整个方法。

如果你不需要锁,把字段声明为volatile是不错的选择,但仍需要确保多线程对该字段的正确访问。可以使用volatile的情况包括:

该字段不遵循其他字段的不变式。

对字段的写操作不依赖于当前值。

没有线程违反预期的语义写入非法值。

读取操作不依赖于其它非volatile字段的值。

当只有一个线程可以修改字段的值,其它线程可以随时读取,那么把字段声明为volatile是合理的。例如,一个名叫Thermometer(中文:体温计)的类,可以声明temperature字段为volatile。正如在3.4.2节所讨论,一个volatile字段很适合作为完成某些工作的标志。另一个例子在4.4节有描述,通过使用轻量级的执行框架使某些同步工作自动化,但是仍需把结果字段声明为volatile,使其对各个任务都是可见的。

原文

Synchronization and the Java Memory Model

Volatile

In terms of atomicity, visibility, and ordering, declaring a field as volatile is nearly identical in effect to using a little fully synchronized class protecting only that field via get/set methods, as in:

final class VFloat {

private float value;

final synchronized void set(float f) { value = f; }

final synchronized float get() { return value; }

}

Declaring a field as volatile differs only in that no locking is involved. In particular, composite read/write operations such as the “++” operation on volatile variables are not performed atomically.

Also, ordering and visibility effects surround only the single access or update to the volatile field itself. Declaring a reference field as volatile does not ensure visibility of non-volatile fields that are accessed via this reference. Similarly, declaring an array field as volatile does not ensure visibility of its elements. Volatility cannot be manually propagated for arrays because array elements themselves cannot be declared as volatile.

Because no locking is involved, declaring fields as volatile is likely to be cheaper than using synchronization, or at least no more expensive. However, if volatile fields are accessed frequently inside methods, their use is likely to lead to slower performance than would locking the entire methods.

Declaring fields as volatile can be useful when you do not need locking for any other reason, yet values must be accurately accessible across multiple threads. This may occur when:

The field need not obey any invariants with respect to others.

Writes to the field do not depend on its current value.

No thread ever writes an illegal value with respect to intended semantics.

The actions of readers do not depend on values of other non-volatile fields.

Using volatile fields can make sense when it is somehow known that only one thread can change a field, but many other threads are allowed to read it at any time. For example, a Thermometer class might declare its temperature field as volatile. As discussed in 3.4.2, a volatile can be useful as a completion flag. Additional examples are illustrated in 4.4, where the use of lightweight executable frameworks automates some aspects of synchronization, but volatile declarations are needed to ensure that result field values are visible across tasks.

volite java_同步和Java内存模型(五)Volatile相关推荐

  1. Java内存模型、volatile、原子性、可见性、有序性、happens-before原则

    目录 1.硬件的效率与一致性: 缓存一致性(Cache Coherence) 2.Java内存模型 2.1主内存与工作内存 2.2内存间的交互 2.3 volatile型变量的特殊规则 2.3.1 保 ...

  2. 【你好面试官】008 Java内存模型指volatile底层原理详解、多处理器原子操作实现原理

    微信公众号:你好面试官 这里没有碎片化的知识,只有完整的知识体系. 专注于系统全面的知识点讲解,面试题目解析; 如果你觉得文章对你有帮助,欢迎关注.分享.赞赏. ###前言 二蛋几天没有收到面试通知, ...

  3. 内存位置访问无效_万字长文——java内存模型之volatile深入解读

    在阅读本文前,请思考以下的面试题? volatile是什么? volatile的特性 volatile是如何保证可见性的? volatile是如何保证有序性的? volatile可以保证原子性吗? 使 ...

  4. java内存模型与volatile变量与Atomic的compareAndSet

    java分主内存和工作内存, 主内存是线程共享的, 工作内存是每个线程独有的. java对主内存的操作是通过工作内存间接完成的: 先拷贝主内存变量值到工作内存, 在工作内存操作这个变量的副本, 完成后 ...

  5. JVM成神之路-Java内存模型(JMM)

    Java 内存模型基础 什么是 Java 内存模型(JMM-共享内存模型) 内存模型描述了程序中各个变量(实例域.静态域和数组元素)之间的关系,以及在实际计算机系统中将变量存储到内存和从内存中取出变量 ...

  6. JSR 133 Java内存模型以及并发编程的最权威论文汇总

    Java内存模型 先看官方文档: https://docs.oracle.com/javase/specs/ JSR 133:Java TM内存模型和线程规范修订版:https://www.jcp.o ...

  7. 深入理解Java内存模型(四)——volatile

    2019独角兽企业重金招聘Python工程师标准>>> volatile的特性 当我们声明共享变量为volatile后,对这个变量的读/写将会很特别.理解volatile特性的一个好 ...

  8. Java内存模型深度解析:volatile--转

    原文地址:http://www.codeceo.com/article/java-memory-4.html Volatile的特性 当我们声明共享变量为volatile后,对这个变量的读/写将会很特 ...

  9. 简单说说你对Java内存模型的原子性的了解吧?

    为什么80%的码农都做不了架构师?>>>    Java内存模型保证non-long.non-double类型外的其他任意类型的访问都是原子性的.同时volatile long.vo ...

最新文章

  1. python黑客攻防入门下载-Python键盘钩取的自我理解(来源于《Python黑客攻防入门》)...
  2. 自适应表格连续字符换行及单行溢出点点点显示
  3. MsSQL ——模拟limit
  4. 中缀表达式转换为后缀表达式算法
  5. 极简毕业设计答辩PPT模板
  6. 模板引擎jade/ejs,模板适配
  7. PostgreSQL SRF函数上索引实现方法
  8. CTF逆向-[CISCN2018]2ex-WP_mips-32架构以及base64换表
  9. PHP+ mysql实现注册登录功能
  10. OrientedRepPoints_DOTA环境搭建训练流程及问题
  11. 2021-10-06---RestTemplate对象
  12. 微信小程序和小游戏自动化测试
  13. 美国,华尔街,某大银行。
  14. 【python】TensorFlow框架下CNN神经网络的花卉识别系统
  15. css 霓虹灯转动效果,CSS3霓虹灯文字动画特效
  16. 性能优化必备——火焰图
  17. 如何导出Axure原型设计中的图片?零基础入门教程
  18. Tomcat启动中文乱码问题
  19. 三级等保测评-服务器设置三权分立
  20. python贷款还款预测

热门文章

  1. 多台主机使用DNS服务器实现网络负载均衡
  2. 软考高级系统架构设计师:DNS负载均衡机制和反向代理的负载均衡机制
  3. 案例拆解 | 教育行业自动化获客和转化
  4. 树莓派4B 安装PIP3
  5. maven install后,java -jar XXXX.jar运行---找不到主类问题 以及 虚拟机中执行jar包后 访问页面出现Java heap space等其他问题
  6. java多线程执行任务
  7. 深圳大学第三期“飞鹰计划”正式开班|学以致用,扬帆起航!
  8. 树莓派开发基础教程目录表
  9. 战地5启动后直接弹回橘子
  10. cnetos 7 安装 nfsen