当前位置: 首页 > news >正文

邢台做网站公司深圳建设局网站首页

邢台做网站公司,深圳建设局网站首页,wordpress多用户主题,企业网站开发总结CAS 详解 一. 什么是 CAS二. CAS 的应用1. 实现原子类2. 实现自旋锁 三. CAS 的 ABA 问题四. 相关面试题 一. 什么是 CAS CAS: 全称Compare and swap#xff0c;字面意思:”比较并交换“一个 CAS 涉及到以下操作#xff1a; 我们假设内存中的原数据 V#xff0c;旧的预期值… CAS 详解 一. 什么是 CAS二. CAS 的应用1. 实现原子类2. 实现自旋锁 三. CAS 的 ABA 问题四. 相关面试题 一. 什么是 CAS CAS: 全称Compare and swap字面意思:”比较并交换“一个 CAS 涉及到以下操作 我们假设内存中的原数据 V旧的预期值 A需要修改的新值 B。 比较 A 与 V 是否相等。比较如果比较相等将 B 写入 V。交换返回操作是否成功。 CAS 伪代码: 下面写的代码不是原子的, 真实的 CAS 是一个原子的硬件指令完成的. 因为本身就是原子操作, 就没有线程安全问题, boolean CAS(address, expectValue, swapValue) {// 取出 address 的值if (address expectedValue) {address swapValue;return true;}return false;}当多个线程同时对某个资源进行CAS操作只能有一个线程操作成功但是并不会阻塞其他线程, 其他线程只会收到操作失败的信号。 可以理解为: CAS 是乐观锁的一种实现方式 二. CAS 的应用 CAS 最大的意义: 为我们写多线程安全的代码提供新的方向和思路 1. 实现原子类 标准库中提供了 java.util.concurrent.atomic 包, 里面的类都是基于这种方式来实现的. 典型的就是 AtomicInteger 类. 其中的 getAndIncrement 相当于 i 操作. AtomicInteger atomicInteger new AtomicInteger(0); // 相当于 i atomicInteger.getAndIncrement();伪代码实现: class AtomicInteger {private int value;public int getAndIncrement() {int oldValue value;while ( CAS(value, oldValue, oldValue1) ! true) {// 没有成功就将期待值换为最新值oldValue value;}return oldValue;} }通过形如上述代码就可以实现一个原子类. 不需要使用重量级锁, 就可以高效的完成多线程的自增操作, 技能保证线程安全又高效, 因为 加锁就涉及到锁竞争, 而 CAS 不涉及线程阻塞. 本来 check and set 这样的操作在代码角度不是原子的. 但是在硬件层面上可以让一条指令完成这个操作, 也就变成原子的了. 2. 实现自旋锁 自旋锁伪代码 public class SpinLock {private Thread owner null;public void lock(){// 通过 CAS 看当前锁是否被某个线程持有. // 如果这个锁已经被别的线程持有, 那么就自旋等待. // 如果这个锁没有被别的线程持有, 那么就把 owner 设为当前尝试加锁的线程. while(!CAS(this.owner, null, Thread.currentThread())){}}public void unlock (){this.owner null;} }三. CAS 的 ABA 问题 ABA 问题: CAS 关键是先比较再交换, 比较实质是比较当前值和旧值是否相同, 若相同, 则视为中间没有发生改变, 就进行修改. 但是这存在漏洞, 可能中间值变化了又变回来了, CAS 就无法判断到底是否发生过改变. 假设存在两个线程 t1 和 t2. 有一个共享变量 num, 初始值为 A. 接下来, 线程 t1 想使用 CAS 把 num 值改成 Z, 那么就需要 先读取 num 的值, 记录到 oldNum 变量中.使用 CAS 判定当前 num 的值是否为 A, 如果为 A, 就修改成 Z. 但是, 在 t1 执行这两个操作之间, t2 线程可能把 num 的值从 A 改成了 B, 又从 B 改成了 A 线程 t1 的 CAS 是期望 num 不变就修改. 但是 num 的值已经被 t2 给改了. 只不过又改成 A 了. 这 个时候 t1 究竟是否要更新 num 的值为 Z 呢? t1 线程无法区分当前这个变量始终是 A, 还是经历了一个变化过程又变为 A 这就好比, 我们买一个手机, 无法判定这个手机是刚出厂的新手机, 还是别人用旧了, 又翻新过的手 机. ABA 问题引来的 BUG: 假设 A 有 100 存款. 想转账给 B 50 块钱. 但是点击转账按钮时没反应, 于是 A 又点击了一次但是取款机实际创建了两个线程, 并发的来执行 -50 操作.我们期望一个线程执行 -50 成功, 另一个线程 -50 失败. 如果使用 CAS 的方式来完成这个扣款过程就可能出现问题: 正常情况,第二个 线程 CAS 期望值是 100, 但实际是 50, 所以扣款失败.但是如果转账过程中 C 又 给 A 转帐 50, 所以第二个线程 CAS 去判断余额还是 100, 所以就会扣款成功. 解决方案: 引入版本号 给要修改的值, 引入版本号. 在 CAS 比较数据当前值和旧值的同时, 也要比较版本号是否符合预期. CAS 操作在读取旧值的同时, 也要读取版本号. 真正修改的时候, 如果当前版本号和读到的版本号相同, 则修改数据, 并把版本号 1.如果当前版本号高于读到的版本号. 就操作失败(认为数据已经被修改过了) 四. 相关面试题 讲解下你自己理解的 CAS 机制 全称 Compare and swap, 即 “比较并交换”. 相当于通过一个原子的操作, 同时完成 “读取内存, 比 较是否相等, 修改内存” 这三个步骤. 本质上需要 CPU 指令的支撑. ABA问题怎么解决 给要修改的数据引入版本号. 在 CAS 比较数据当前值和旧值的同时, 也要比较版本号是否符合预期. 如果发现当前版本号和之前读到的版本号一致, 就真正执行修改操作, 并让版本号自增; 如果发现当前版本号比之前读到的版本号大, 就操作失败. 相对于 锁机制, 为什么 CAS 效率更高? 因为 CAS 本身就是一组原子指令, 不涉及线程安全问题, 所以不需要加锁、解锁等开销减少了线程在互斥同步时所产生的性能消耗当多个线程同时进行 CAS 操作时只有一个能成功其余则需重试不涉及线程阻塞. 好啦 以上就是对 CAS 的讲解希望能帮到你 评论区欢迎指正 !
http://www.w-s-a.com/news/775371/

相关文章:

  • 网站建设合约品牌设计有哪些
  • 织梦企业门户网站宝塔搭建wordpress网站
  • 网站为什么没有排名了11月将现新冠感染高峰
  • 网站开发维护专员岗位职责辽阳企业网站建设
  • 做外国订单有什么网站网站设计论文提纲
  • 商城网站建设报价方案导师让做网站
  • 清远市企业网站seo联系方式动易官方网站
  • 手机上怎么做能打开的网站一级域名和二级域名跨域
  • 网站首页效果图wordpress 在线教育
  • 电商网站开发团队广西桂林商贸旅游技工学校
  • 网站模板文件怎么下载东莞常平镇邮政编码
  • 建网站需要什么wordpress误删的后果
  • wordpress无插件实现网站地图做阿里巴巴网站店铺装修费用
  • 英文互动网站建设南宁住房和城乡建设局网站
  • 威海微网站建设乐清建网站哪家强
  • 网站和app的开发成本saas系统开发教程
  • ps切片工具做网站大气简洁网站
  • 网至普的营销型网站建设wordpress邮箱验证插件下载
  • 找权重高的网站方法张家港早晨网站建设
  • WordPress数据库添加管理员关键词优化举例
  • 河南国基建设集团--官方网站wordpress qode
  • 做农村电子商务的网站有哪些内容静态网站模板古典
  • 导航网站设计方案个人网站推广方法
  • 网站排名易下拉教程防wordpress花园
  • 计算机网站建设 是什么意思现在网站建站的主流语言是什么
  • php网站跟随导航西安百姓网免费发布信息网
  • 濮阳做公司网站html5 特效网站
  • ppt设计器怎么打开深圳seo网络推广营销
  • 建设银行网站用360浏览器建设信用卡中心网站
  • 创建公司网站 教程广州建设局