CAS个人理解

CAS原理讲解(个人理解) CAS原理: 比较并交换:(compareAndSet) 主物理内存的值与线程的期的望值一致的话, 就进行修改;不同的话,就不能进行修改; package CAS; import java.util.concurrent.atomic.AtomicInteger; public class CASdemo01 { public static void main(String[] args) { //物理内存中值: 5 AtomicInteger atomicInt 阅读详情

CAS是什么?

CAS(Compare And Swap)是一条cup并发原语,其本质是比较并交换。

CAS实例

public class CASDemo {
    public static void main(String[] args) {
        AtomicInteger atomicInteger = new AtomicInteger(5);
        atomicInteger.compareAndSet(5, 2019);
        System.out.println(atomicInteger.get());
        atomicInteger.compareAndSet(2019, 2000);
        System.out.println(atomicInteger.get());
        }
  }

CAS的底层

自旋锁 + Unsafe类

什么是Unsafe类

由于java无法直接访问的底层系统内存,不像c语言那样可以直接通过指针,访问变量的存储地址。java需要通过本地方法访问底层系统数据存储地址,而Unsafe类弥补了 这一局限性,相当于一个后门。Unsafe提供了很多的native方法可以直接访问操作特定内存的数据。与c语言的指针类似。

什么是自旋锁

自旋锁是一种为了保护共享资源而提出的一种锁机制。

代码原理如下:

 public final int getAndAddInt(Object var1, long var2, int var4) {
        int var5;
        do {
            var5 = this.getIntVolatile(var1, var2);
        } while(!this.compareAndSwapInt(var1, var2, var5, var5 + var4));

        return var5;
    }

在上面的代码中
var1 就是对象进行操作的对象引用
var2 是该对象引用在内存的偏移量,也就是起始地址
var5 是期望值
var5 + var4 是待更新的值
这段代码的含义就是根据共享变量的存储地址获取该变量的值,判断该变量的值是否等于期望值,如果相等则将待更新主内存中该变量的值为最新的值。反之,继续进行比较,直到主内存中的值和期望值一致为止。
CAS并发原语体现在Java语言就是Unsafe类的各个方法,java条用Unsafe类的方法,JVM会自动帮我们实现CAS的汇编指令,这是一种完全依赖于硬件的功能,通过它体现了原子性操作,CAS是系统原语,属于操作系统指令,由若干条指令组成的代码块,执行必须是连续性,中间不能被中断。

CAS的缺点:
1、循环时间长,内存消耗大;
如果线程数量比较多的话,CAS请求失败会一直循环下去,这样的话CPU的开销会比较大。
2、只能对一个共享变量进行原子性的操作
3、会出现ABA问题。

什么是ABA问题?
由于CAS无法对主内存共享变量的操作记录,比如,更改次数,是否更改。这容易让一个线程将给A修改成B,而另一个线程又将B修改成A造成CAS多次执行的问题。也就是开头和结尾是一样的,中间过程发生了变化。
原子引用
原子引用AtomicReference是保证基本类型的原子性,对于一个类而言,可以使用原子引用进行封装。

AtomicReference<User> userAtomic =  new AtomicReference<>();

如何解决ABA问题
ABA问题的本质就是通过CAS多次改变了主内存的共享变量的值,而最终又改为最初的值。头尾一样,中间的操作对于其他线程来说是不可知的,这可能会造成CAS的多次执行。
而想要解决ABA问题的办法就是让其他线程能够知道这个变量中间有被更改过,我们只在变量每一次被修改时添加一个记录就可以解决了这个一个问题。
AtomicStampedReference 在原有的AtomicReference上添加了版本号的概念。
使用案例

public class ABADemo { //ABA解决问题,AtomicStampedReference

    static AtomicReference<Integer> atomicReference = new AtomicReference<>(100);
    static AtomicStampedReference<Integer> atomicStampedReference = new AtomicStampedReference<>(100, 1);
    public static void main(String[] args) {
        new Thread(()->{
            atomicReference.compareAndSet(100, 101);
            atomicReference.compareAndSet(101, 100);
        }, "t1").start();
        new Thread(()->{
            try {
                TimeUnit.SECONDS.sleep(1);
            }catch (InterruptedException e){
                e.printStackTrace();
            }
            System.out.println(atomicReference.compareAndSet(100, 100) + "\t" + atomicReference.get());
        },  "t2").start();
        try {
            TimeUnit.SECONDS.sleep(1);
        }catch (InterruptedException e){
            e.printStackTrace();
        }

        System.out.println("*******************演示ABA的解决********************");
        new Thread(()->{
            int stamp = atomicStampedReference.getStamp(); //获取版本号
            System.out.println(Thread.currentThread().getName() + "当前版本号:" + stamp);
            try { TimeUnit.SECONDS.sleep(1); }catch (InterruptedException e){ e.printStackTrace();}
            atomicStampedReference.compareAndSet(100, 101, atomicStampedReference.getStamp(), atomicStampedReference.getStamp() + 1);
            System.out.println(Thread.currentThread().getName() + "当前版本号:" + atomicStampedReference.getStamp());
            atomicStampedReference.compareAndSet(101, 100, atomicStampedReference.getStamp(), atomicStampedReference.getStamp() + 1);
            System.out.println(Thread.currentThread().getName() + "当前版本号:" + atomicStampedReference.getStamp());
        }, "t3").start();

        new Thread(()->{
            int stamp = atomicStampedReference.getStamp();
            System.out.println(Thread.currentThread().getName() + "当前版本号:" + atomicStampedReference.getStamp());
            try{ TimeUnit.SECONDS.sleep(3);}catch (InterruptedException e){e.printStackTrace();}
           boolean result =  atomicStampedReference.compareAndSet(100, 2019, stamp, stamp + 1);
            System.out.println(Thread.currentThread().getName() + "修改成功?" + result + "当前最新版本号" + atomicStampedReference.getStamp());
            System.out.println(Thread.currentThread().getName() + "当前线程实际最新值" + "\t" + atomicStampedReference.getReference());
        }, "t4").start();
    }
}

使用时间戳原子引用,当某个线程在修改值时,发现虽然内存中的值和预期值一样,但是由于版本号已经发生了该改变,所以修改失败,这时候需要重新获取该变量的版本号和变量的值再进行修改,并标记新的为新的版本。

揭秘CAS:深入理解与应用解析 在并发编程中,Compare-And-Swap(CAS)机制作为一种无锁算法,凭借其高效性和避免线程阻塞的优势,受到广泛关注。CAS不仅在底层实现上有着重要地位,还在实际开发中发挥着关键作用。本文将从CAS的工作原理、在Java中的实现及其增强机制来回顾和加深理解一下CAS。 阅读详情

相关推荐

[cryoEM] cryoSPARC简介

cryoSPARC系统结构概述 cryoSPARC是一个后端和前端高性能计算软件系统,为单颗粒冷冻电镜提供数据处理和图像分析能力,以及丰富的基于浏览器的用户截面和命令行工具。 Master-worker模式 系统基于主用户模式。 主进程(web应用,核心应用程序和MongoDB数据库)一起在主节点上运行。主节点需要相对轻量级的资源(2+ CPU< 16GB+ RAM)。 工作程序进程可以在具有GPU的任何可用节点上生成,负责所有实际计算和数据处理,并由主节点调度。注意:同一节点可以同时充当主节点和辅

进阶中的程序员吃吃的博客 7797

【并发编程】CAS到底是什么

CAS是Compare-And-Swap(比较并交换)的缩写,是一种轻量级的同步机制,主要用于实现多线程环境下的无锁算法和数据结构,保证了并发安全性。它可以在不使用锁(如synchronized、Lock)的情况下,对共享数据进行线程安全的操作。

陈宝子的博客 9268

混合编程实战:C#集成C++ PCL点云处理库,打造跨语言动态链接库

本文详细介绍了C#与C++混合编程实战,重点讲解如何通过动态链接库(DLL)集成C++ PCL点云处理库,实现跨语言协作。内容涵盖环境配置、PCL功能封装、C#调用DLL的完整方案,以及性能优化和错误处理等进阶技巧,帮助开发者高效处理大规模点云数据,提升工业软件开发效率。

weixin_42620913的博客 382

CAS的原理和使用

你只需要记住:CAS是靠硬件实现的从而在硬件层面提升效率,最底层还是交给硬件来保证原子性和可见性实现方式是基于硬件平台的汇编指令,在intel的CPU中(X86机器上),使用的是汇编指令cmpxchg指令。核心思想就是:比较要更新变量的值V和预期值E(compare),相等才会将V的值设为新值N(swap)如果不相等自旋再来。可以丢入泛型中Class AtomicReference案例int age;

weixin_43869741的博客 2835

Pi0 项目复现及项目问题解决方案(全网抢先发布~)

Pi0 项目复现及项目问题解决方案(全网抢先发布~)

m0_68167062的博客 2261

WiFi信道状态信息 基于Intel 5300的CSI Tool 安装及使用(一)

经过半个月的坎坷安装过程,连Windows系统都没装过的本人终于颤颤巍巍把CSI TOOL装好了,下面记录一下适于我所使用设备的安装过程。设备:一台THINKPAD X201,一台师兄借的华硕主板的台式机首先,如果你和我一样对linux其实一窍不通的话,建议先反复看教程里的安装代码,照猫画虎很难一步实现的,中途一定会有这或那的问题需要解决,所以该了解的基础linux指令还是要了解,起码安装过程中的那些指令可以去查一查。.........

Silver_777的博客 2万+

SSO(单点登录)实施中遇到的几个问题

单点登录应用中,遇到如下的几个问题:1.超时问题;2.jsessionid问题;3.单点退出时有时子系统未能正常退出;4.有些请求路径不需要单点登录过滤器拦截;5.不同应用服务实现可能要求SSO客户端做适应性改造。我们具体分析一下,并提出解决方法。 1.超时问题         我们提供的CAS开源单点登录SSO组件,它部署节点主要有2个:SSO服务器(部署内容为一个web应用)、应用系统

yan_dk的专栏 1万+

PyTorch实战:手把手教你用QAT量化感知训练拯救模型精度(附避坑指南)

本文详细介绍了如何使用PyTorch进行QAT量化感知训练,以提升模型在边缘设备上的推理精度。通过核心原理讲解、实战代码示例和避坑指南,帮助开发者掌握从环境配置、模型训练到边缘部署的全流程,有效解决传统量化方法导致的精度损失问题。

c7d8e的博客 329

深入理解Java多线程CAS比较并交换的底层原理

一.多线程环境下的自增操作 我们都知道在多线程情况下 i++ 的自增操作不是原子性的,因为它分为三个步骤: 取得i的值 将i的值+1 将新值写回内存 所以我们会使用JUC包下的AtomicInteger类来进行int的原子操作: public final int addAndGet(int delta) { return unsafe.getAndAddInt(this, va...

atomatom98的博客 471

【ArcGIS Pro微课1000例】0023:ArcGIS Pro 3.0中打开GeoPackage数据库(.gpkg)

本文讲解ArcGIS Pro 3.0中打开GeoPackage数据库(.gpkg)的两种方法。

智慧空间实验室 4643

《MPDIoU:边界框回归的高效革新与YOLOv8集成实战指南》

摘要: MPDIoU(多优先级距离IoU)通过引入中心距离、形状差异和尺度变化的三步优化策略,解决了传统IoU在目标检测中的尺度敏感、收敛低效和场景局限问题。相较于GIoU、DIoU等主流方法,MPDIoU在精度、速度和鲁棒性上实现全面提升,尤其在复杂场景和小目标检测中表现突出。通过代码集成和训练优化,MPDIoU在YOLOv8中显著提升COCO数据集AP指标,并在智能安防(密集行人检测)和工业质检(微小缺陷定位)等垂直领域验证了其应用价值。未来研究方向包括动态权重调整和多模态融合,进一步拓展边界框回归的精

m0_64661770的博客 158

Java中CAS详解

在JDK 5之前Java语言是靠synchronized关键字保证同步的,这会导致有锁 锁机制存在以下问题: (1)在多线程竞争下,加锁、释放锁会导致比较多的上下文切换和调度延时,引起性能问题。 (2)一个线程持有锁会导致其它所有需要此锁的线程挂起。 (3)如果一个优先级高的线程等待一个优先级低的线程释放锁会导致优先级倒置,引起性能风险。 volatile是不错的机制

jayxu无捷之径的博客 20万+

3、图像中文字信息提取技术全解析

本文全面解析了图像中文字信息提取(Text Information Extraction,TIE)的技术原理、挑战及应用领域。详细介绍了图像中三种主要文字形式:场景文字、字幕文字和文档文字的特点及提取难点。系统阐述了TIE技术的主要流程步骤,包括文字检测、定位、提取与增强、识别等关键阶段,并对主流技术方法进行了分类比较,包括基于连通组件、边缘、纹理等方法的优缺点分析。文章还介绍了多种其他提取技术,如二值化方法、混合方法、基于梯度的方法等,并提出了一种基于立体帧的新型场景文字提取方法,通过实验验证了该方法在召

ll5678的博客 119

对CAS的一点个人理解

在Java中,JDK 1.5之后可以使用CAS(Compare-and-Swap)操作。CAS的思想就是:先将旧期待值与主内存中值作比较,如果相同,那么就接受新的值,否则就不进行任何操作,这种处理过程是一个原子操作。 CAS帮助我们实现非阻塞同步策略,这是一种乐观并发策略,乐观就是指它总是假设其他线程不会打扰自己,所以会先进行操作,如果有冲突,再采取一定措施,比如一直重试直到成功为止。这种策略的...

Shelby Lee的博客 412

pscad IEEE标准系统搭建说明

pscad IEEE标准系统搭建说明,包含典型的IEEE 9节点、14节点、30节点、39节点和118节点系统。内含标准测试系统的原始数据和潮流结果。

efm32 入门.pdf

本PDF共计22页,介绍的是操作驱动API,下载与否自己斟酌。

CAS的个人理解

什么是CAS CAS是Compare And Swap即比较并交换的缩写。 CAS需要有3个操作数:内存地址V,旧的预期值A,即将要更新的目标值B。 CAS指令执行时,当且仅当内存地址V的值与预期值A相等时,将内存地址V的值修改为B,否则就什么都不做。整个比较并替换的操作是一个原子操作(因为调用了CPU提供的指令,intel CPU中为cmpxchg)。 CAS一般是配合无限循环使用的。 CAS的三个问题 ABA问题 循环时间开销很大 只能保证一个变量的原子操作 ABA问题 因为CAS需要在操作值的时候

Nana77mi的博客 232

计算机控制技术及应用

《计算机控制技术及应用》通过总结作者的科研成果和吸收国内外的先进理论、方法和技术,以计算机控制系统的网络化、开放化、智能化和集成化发展趋势为主线索,主要介绍计算机控制系统的基本概念和计算机控制系统的典型形式,计算机控制系统的数学描述与基本分析方法,以及数字PID控制器、最少拍控制系统、达林算法、状态变量设计法等设计方法及其各种改进算法。重点突出计算机控制系统输入输出通道接口的设计方法和典型控制系统的设计案例与实现方法等。

CAS算法个人理解

一、描述 在日常的开发中,经常会出现多个线程去同时操作一个变量的情况。在这种情况下,我们经常会将此变量加上synchronized修饰符,来保证同一时间内只能有一个线程去访问修改该变量,但这样其他的县城都必须挂起,效率非常低。所以出现了一种新的思想:也就是CAS算法。 CAS算法全名为Compare And Swap 算法,即比较-替换算法。 这种算法有三个变量,内存地址的值V,旧的预期值A...

StartLine 285

Statistics and Machine Learning Toolbox

Statistics and Machine Learning Toolbox(带书签),MATLAB统计学习工具

cas_个人理解

原网址:https://www.cnblogs.com/gossip/p/5651379.html 总结的非常好的文章,值得分享! 分为三个部分: 1、Cas服务器(用于验证用户是否正确) 1、用户信息存在服务端,其它客户端应用程序修改用户信息后需要同步到服务端 2、用户信息一般存储在服务端的数据库中,加密及验证算法Cas提供默认方法 2、Cas客户端(和应用程序合为一体) 3、客户端(一般是用户...

qq_38949960的博客 414

Cas_个人理解

分为三个部分: 1、Cas服务器(用于验证用户是否正确) 1、用户信息存在服务端,其它客户端应用程序修改用户信息后需要同步到服务端 2、用户信息一般存储在服务端的数据库中,加密及验证算法Cas提供默认方法 2、Cas客户端(和应用程序合为一体) 3、客户端(一般是用户使用的web浏览器) 名词解释 http://www.coin163.com...

weixin_33910460的博客 134

JUC并发编程学习笔记——CAS个人理解

即compare and swap(比较与交换),是一种有名的无锁算法。无锁编程,即不使用锁的情况下实现多线程之间的变量同步,也就是在没有线程被阻塞的情况下实现变量的同步,所以也叫非阻塞同步(Non-blocking Synchronization)。

程哥哥的一亩三分地 338

什么是CAS单点登录

早上遇到别人说的CAS单点登录问题,俺在一旁一头雾水,就看了一下什么是CAS单点登录,由于度娘上基本没有关于什么CAS单点登录,都是说怎么部署的,所以写一下这篇东西记录一下个人理解。 场景:由于一个公司的web应用有很多,每个应用的登录系统都不一样,当同一个用户访问一个公司的应用时,我们不可能要让他登录多次(ps:例如腾讯有很多应用,QQ,空间,邮箱,游戏等等),CAS单点登录就是为了...

u010314099的博客 233

CAS理解和说明

然而,ABA问题是一个潜在的问题,即在CAS操作过程中,一个变量的值被修改两次后又恢复到了原来的值,导致CAS误判为没有发生变化,这个问题就叫ABA问题。完成的,所以CAS操作是原子的,就可以在一定程度上回避线程安全问题,所以我们在解决线程安全问题除了加锁之外,又有了一个新思路。此时的value值变成1,但是CAS的返回值为true,所以oldValue的值仍然为0。在这里最特别的是,上述这个CAS的过程,并非是通过一段代码实现的,而是通过。我们假设内存中的原始数据V,旧的预期值A,需要修改的新值B。

m0_62055442的博客 1889

Java中的CAS理解

Java中的CAS理解CAS是什么?CAS能做什么?CAS在java中的应用CAS有没有什么不好的隐患呢?1、首先就是经典的ABA问题2、长时间自旋非常消耗资源3、只能保证一个共享变量的原子操作。 在JDK 5之前Java语言是靠synchronized关键字保证同步的,这会导致有锁 锁机制存在以下问题: (1)在多线程竞争下,加锁、释放锁会导致比较多的上下文切换和调度延时,引起性能问题。 (2)一个线程持有锁会导致其它所有需要此锁的线程挂起。 (3)如果一个优先级高的线程等待一个优先级低的线程释放锁会导致

@龙猫的博客 2457

CAS详解,如何理解CAS!

CAS是英文单词Compare and Swap的缩写,翻译过来就是比较并替换。 CAS机制中使用了3个基本操作数:内存地址V,旧的预期值A,要修改的新值B。 更新一个变量的时候,只有当变量的预期值A和内存地址V当中的实际值相同时,才会将内存地址V对应的值修改为B。 我们看一个例子: 在内存地址V当中,存储着值为10的变量。 2. 此时线程1想把变量的值增加1.对线程1来说,旧的预期值A=10,要修改的新值B=11. 3. 在线程1要提交更新之前,另一个线程2抢先一步,把内存地址V中的变量值率先更新

Pumpkin's Blog 2240

CAS的理解

CAS 的全称 Compare-And-Swap,它是一条 CPU 并发操作。 jdk1.5开始,并发包里提供了一些类支持原子操作,,如 AtomicInteger,这些原子包装类还提供了有用的工具方法,比如以原子的方式对当前对象进行+1或者-1;Java并发框架包中有一些并发框架使用了CAS自旋锁的方式来实现原子操作,CAS虽然解决了原子操作的问题,但是仍然存在三大问题。ABA问题,循环时间长开...

qq_35529931的博客 1104
上一篇: 解决IDEA写代码卡顿问题
下一篇: 震惊! Docker启动tomcat访问竟然报404?看看这位小伙子如何处理!
小码林marlin
博客等级 码龄9年 30粉丝 29原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值