CAS核心思想、底層實現
★ 1、CAS 是什麼
CAS 是比較並交換,是實現併發算法時常用到的一種技術。 當內存的值和期望的值相等時,進行更新 ,否則 什麼都不做 或 重來 。
CAS 的底層實現:是靠硬件實現的,靠硬件的原子性實現, CAS是一條CPU的原子指令 ( cmpxchg指令 ), 不會造成所謂的數據不一致問題 。
重來==> 自旋
CAS 類似樂觀鎖,樂觀的認為別人沒有修改,當值還是預期值,就進行修改,否則可能什麼都不做,或者重來。
★ 2、CAS 應用舉例
- 原子操作類,比如整型的原子操作類的compareAndSet方法
- 我的博客項目中,在更新文章瀏覽次數時,當前 內存的文章瀏覽次數 和 期望中的 數據庫的文章瀏覽次數 進行比較,如果是相同的,則加1,否則 什麼都不做
3、原子類
■ 原子類==> 底層思想/工作原理 CAS ==> Unsafe 類的CPU 原語級別的彙編操作
-
CAS 是靠硬件實現的,靠硬件的原子性實現 , CAS是一條CPU的原子指令 ( cmpxchg指令 ), 不會造成所謂的數據不一致問題 ,
Unsafe提供的CAS方法(如compareAndSwapXXX)底層實現即為CPU指令cmpxchg。
■ AtomicInteger 類主要利用 CAS + volatile 和 native 方法來 保證原子操作,從而避免 synchronized 的高開銷 ,執行效率大為提升。
new AtomicInteger().compareAndSet(0, 1); // 底層實現 public final int getAndAdd(int delta) { return unsafe.getAndAddInt(this, valueOffset, delta); } public final boolean compareAndSet(int expect, int update) { return unsafe.compareAndSwapInt(this, valueOffset, expect, update); } new AtomicInteger().getAndAdd(1);//獲取到當前值並加1 // 底層實現 public final int getAndAdd(int delta) { return unsafe.getAndAddInt(this, valueOffset, delta); } 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; }
■ 工作中,不建議使用Unsafe 類,類名就提示你了"不安全"!
4、Unsafe 類
-
是CAS的核心類
-
可以
像C的指針一樣直接操作內存
-
Unsafe類中的所有方法都是native修飾的
,Unsafe類中的方法都可以直接調用操作系統底層資源去執行相應任務
//原子類 public final int getAndIncrement() { return unsafe.getAndAddInt(this, valueOffset, 1); } private volatile int value;
變量 valueOffset ,表示該變量值在內存中的 偏移地址 ,因為 Unsafe就是根據內存偏移地址獲取數據 的。
變量value用volatile修飾,保證了多線程之間的內存可見性。每次獲取的值都是最新的。
5、CAS 帶來的問題
- 循環時間長,可能死循環,開銷很大
-
ABA 問題
- 解決ABA 問題: 帶版本號的原子引用 AtomicStampedReference
如果本文對你有幫助的話記得給一樂點個贊哦,感謝!
「其他文章」
- 線程池底層原理詳解與源碼分析
- 30分鐘掌握 Webpack
- 線性迴歸大結局(嶺(Ridge)、 Lasso迴歸原理、公式推導),你想要的這裏都有
- 【前端必會】webpack loader 到底是什麼
- 中心化決議管理——雲端分析
- HashMap底層原理及jdk1.8源碼解讀
- 詳解JS中 call 方法的實現
- 打印 Logger 日誌時,需不需要再封裝一下工具類?
- 初識設計模式 - 代理模式
- 密碼學奇妙之旅、01 CFB密文反饋模式、AES標準、Golang代碼
- Springboot之 Mybatis 多數據源實現
- CAS核心思想、底層實現
- 面試突擊86:SpringBoot 事務不回滾?怎麼解決?
- 基於electron vue element構建項目模板之【打包篇】
- MiniWord .NET Word模板引擎,藉由Word模板和數據簡單、快速生成文件。
- 認識線程,初始併發
- 1-VSCode搭建GD32開發環境
- 初識設計模式 - 原型模式
- 線程安全問題的產生條件、解決方式
- 2>&1到底是什麼意思?