锁专题(三)工作5年了,竟然不知道 volatile 关键字( 四 )
< V > implements java.io.Serializable {private volatile V value;//省略其他代码 }为什么追加64字节能够提高并发编程的效率呢?因为对于英特尔酷睿i7 , 酷睿 ,Atom和NetBurst ,Core Solo和Pentium M处理器的L1 , L2或L3缓存的高速缓存行是64个字节宽 , 不支持部分填充缓存行 , 这意味着如果队列的头节点和尾节点都不足64字节的话 , 处理器会将它们都读到同一个高速缓存行中 , 在多处理器下每个处理器都会缓存同样的头尾节点 , 当一个处理器试图修改头接点时会将整个缓存行锁定 , 那么在缓存一致性机制的作用下 , 会导致其他处理器不能访问自己高速缓存中的尾节点 , 而队列的入队和出队操作是需要不停修改头接点和尾节点 , 所以在多处理器的情况下将会严重影响到队列的入队和出队效率 。
Doug lea使用追加到64字节的方式来填满高速缓冲区的缓存行 , 避免头接点和尾节点加载到同一个缓存行 , 使得头尾节点在修改时不会互相锁定 。
- 那么是不是在使用Volatile变量时都应该追加到64字节呢?
在两种场景下不应该使用这种方式 。
第一:缓存行非64字节宽的处理器 , 如P6系列和奔腾处理器 , 它们的L1和L2高速缓存行是32个字节宽 。
第二:共享变量不会被频繁的写 。
因为使用追加字节的方式需要处理器读取更多的字节到高速缓冲区 , 这本身就会带来一定的性能消耗 , 共享变量如果不被频繁写的话 , 锁的几率也非常小 , 就没必要通过追加字节的方式来避免相互锁定 。
ps: 忽然觉得术业想专攻 , 博学与睿智缺一不可 。
double/long 线程不安全Java虚拟机规范定义的许多规则中的一条:所有对基本类型的操作 , 除了某些对long类型和double类型的操作之外 , 都是原子级的 。
目前的JVM(java虚拟机)都是将32位作为原子操作 , 并非64位 。
当线程把主存中的 long/double类型的值读到线程内存中时 , 可能是两次32位值的写操作 , 显而易见 , 如果几个线程同时操作 , 那么就可能会出现高低2个32位值出错的情况发生 。
要在线程间共享long与double字段时 , 必须在synchronized中操作 , 或是声明为volatile 。
小结volatile 作为 JMM 中非常重要的一个关键字 , 基本也是面试高并发必问的知识点 。
希望本文对你的工作学习面试有所帮助 , 如果有其他想法的话 , 也可以评论区和大家分享哦 。
各位极客的点赞收藏转发 , 是老马写作的最大动力!
文章插图
【锁专题(三)工作5年了,竟然不知道 volatile 关键字】深入学习
- 采用|消息称一加9系列将推出三款新机,新增一加9E
- 同比|亚马逊公布“剁手节”创纪录战绩:第三方卖家全球销售额超48亿美元 同比大增60%
- 王文鉴|从工人到千亿掌门人,征服华为三星,只因他36年只坚持做一件事
- 俄罗斯手机市场|被三星、小米击败,华为手机在俄罗斯排名跌至第三!
- 操盘|中兴统一操盘中兴、努比亚、红魔三大品牌
- 责令|1336款APP被责令整改,三大问题突出
- 三个目标之后|品味莲乡 | 品味
- 苹果|iPhone13迎来变化!或回归指纹解锁,这几点备受用户喜爱
- 星期一|亚马逊:黑五与网络星期一期间 第三方卖家销售额达到48亿美元
- 短视频平台|大数据佐证,抖音带动三千万就业,视频手机将成生产力工具?