AtomicReference通过CPU的CAS指令实现引用的无锁原子更新,核心是compareAndSet等方法以原子方式完成“读取—比较—设置”,失败时返回false并可循环重试,不依赖synchronized或锁机制。

AtomicReference 通过底层的 CAS(Compare-And-Swap)指令 实现对象引用的原子更新,不依赖锁,而是利用 CPU 提供的原子硬件指令来保证线程安全。
核心机制:CAS 操作
AtomicReference 的所有原子更新方法(如 compareAndSet、getAndSet、updateAndGet)都基于 CAS。其逻辑是:
- 读取当前引用值(记为
expected) - 比较当前值是否仍等于
expected - 如果相等,则将引用更新为新值,并返回
true;否则返回false,不修改
这个“比较 + 设置”过程由 JVM 调用本地方法(如 Unsafe.compareAndSwapObject)完成,在 x86 上通常编译为一条 cmpxchg 汇编指令,由 CPU 硬件保证原子性。
为什么能避免锁,又保证线程安全?
CAS 是乐观策略:它假设冲突较少,先尝试更新,失败再重试。关键点在于:
立即学习“Java免费学习笔记(深入)”;
- 整个 CAS 操作不可中断,不会被其他线程插入执行
- 即使多个线程同时调用
compareAndSet,最多只有一个能成功(因为一旦某个线程更新了值,其余线程看到的“当前值”就变了) - 没有锁膨胀、上下文切换或阻塞开销
典型使用方式:配合循环实现无锁更新
要实现可靠的原子修改(比如对对象字段做自增),常采用“读-改-写”循环模式:
AtomicReference<Counter> ref = new AtomicReference<>(new Counter(0));
// 原子地将 count 加 1
Counter current, next;
do {
current = ref.get();
next = new Counter(current.count + 1);
} while (!ref.compareAndSet(current, next));
注意:这里要求被包装的对象是**不可变的**(如 Counter 的 count 是 final),否则即使引用替换成功,内部状态仍可能被其他线程非原子修改。
与 volatile 引用的区别
volatile 只保证引用本身的可见性和禁止重排序,但不保证复合操作(如“读旧值 → 计算新值 → 写入”)的原子性;而 AtomicReference 的 compareAndSet 等方法把这三步打包成一个原子操作,这才是真正支持无锁并发编程的关键。


















