一、原子类

1、CAS算法

  强烈建议读者看这篇之前,先看这篇 初识JUC 的前两节,对原子性,原子变量,内存可见性有一个初步认识。

  CAS(Compare and Swap)是一种硬件对并发的支持,针对多处理器操作而设计的处理器中的一种特殊指令,用于管理对共享数据的并发访问,是硬件对于并发操作共享数据的支持。它是一个原子性的操作,对应到CPU指令为cmpxchg。它是一条CPU并发原语。
  CAS包含了3个操作数:内存值V,比较值A,更新值B。当且仅当V == A时,V = B,否则不执行任何操作。
  CAS算法:当多个线程并发的对主存中的数据进行修改的时候。有且只有一个线程会成功,其他的都会失败(同时操作,只是会失败而已,并不会被锁之类的)。
  CAS是一种无锁的非阻塞算法,是乐观锁的一种实现。不存在上下文切换的问题。
  CAS比普通同步锁效率高,原因:CAS算法当这一次不成功的时候,它下一次不会阻塞,也就是它不会放弃CPU的执行权,它可以立即再次尝试,再去更新。
  通俗的说:我要将变量 i 由 2 修改为 3。当内存中 i == 2,且修改成功,才为成功。若内存中 i 由于其他线程的操作已经不是 2 了,那此次我的修改视为失败。

2、简单使用

  JDK 1.5 以后java.util.concurrent.atomic包下提供了常用的原子变量。它支持单个变量上的无锁线程安全编程。这些原子变量具备以下特点:volatile的内存可见性;CAS算法保证数据的原子性。

  atomic包描述:图片来源API文档

聊聊并发(六)——CAS算法-LMLPHP

  代码示例:原子变量使用

 1 public class Main {
 2     public static void main(String[] args) {
 3         AtomicInteger integer = new AtomicInteger(2);
 4
 5         boolean b = integer.compareAndSet(3, 5);
 6         System.out.println(b);
 7         System.out.println(integer.get());
 8
 9         b = integer.compareAndSet(2, 10);
10         System.out.println(b);
11         System.out.println(integer.get());
12
13         // 等价于 i++
14         integer.getAndIncrement();
15
16         // 等价于 ++i
17         integer.incrementAndGet();
18     }
19 }
20
21 // 结果
22 false
23 2
24 true
25 10
12-02 14:17