1. 程式人生 > >Java多線程系列---“JUC原子類”05之 AtomicReference原子類

Java多線程系列---“JUC原子類”05之 AtomicReference原子類

系列 void test sys 源碼 lap ava 線程 http

轉自:http://www.cnblogs.com/skywang12345/p/3514623.html(部分修改)

概要

本章對AtomicReference引用類型的原子類進行介紹。內容包括:

  • AtomicReference介紹和函數列表
  • AtomicReference源碼分析(基於JDK1.7.0_40)
  • AtomicReference示例

AtomicReference介紹和函數列表

AtomicReference是作用是對"對象"進行原子操作。

AtomicReference函數列表

// 使用 null 初始值創建新的 AtomicReference。
AtomicReference()
// 使用給定的初始值創建新的 AtomicReference。
AtomicReference(V initialValue) // 如果當前值 == 預期值,則以原子方式將該值設置為給定的更新值。 boolean compareAndSet(V expect, V update) // 獲取當前值。 V get() // 以原子方式設置為給定值,並返回舊值。 V getAndSet(V newValue) // 最終設置為給定值。 void lazySet(V newValue) // 設置為給定值。 void set(V newValue) // 返回當前值的字符串表示形式。 String toString() // 如果當前值 == 預期值,則以原子方式將該值設置為給定的更新值。
boolean weakCompareAndSet(V expect, V update)

說明
AtomicReference的源碼比較簡單。它是通過"volatile"和"Unsafe提供的CAS函數實現"原子操作。
(01) value是volatile類型。這保證了:當某線程修改value的值時,其他線程看到的value值都是最新的value值,即修改之後的volatile的值。
(02) 通過CAS設置value。這保證了:當某線程池通過CAS函數(如compareAndSet函數)設置value時,它的操作是原子的,即線程在操作value時不會被中斷。

技術分享圖片
 1 package com.test.a;
2 3 //AtomicReferenceTest.java的源碼 4 import java.util.concurrent.atomic.AtomicReference; 5 6 public class AtomicReferenceTest { 7 8 public static void main(String[] args) { 9 10 // 創建兩個Person對象,它們的id分別是101和102。 11 Person p1 = new Person(101); 12 Person p2 = new Person(102); 13 // 新建AtomicReference對象,初始化它的值為p1對象 14 AtomicReference ar = new AtomicReference(p1); 15 // 通過CAS設置ar。如果ar的值為p1的話,則將其設置為p2。 16 ar.compareAndSet(p1, p2); 17 18 Person p3 = (Person) ar.get(); 19 System.out.println("p3 is " + p3); 20 System.out.println("p3.equals(p1)=" + p3.equals(p1)); 21 } 22 } 23 24 class Person { 25 volatile long id; 26 27 public Person(long id) { 28 this.id = id; 29 } 30 31 public String toString() { 32 return "id:" + id; 33 } 34 }
View Code 技術分享圖片
1 p3 is id:102
2 p3.equals(p1)=false
View Code

結果說明
新建AtomicReference對象ar時,將它初始化為p1。
緊接著,通過CAS函數對它進行設置。如果ar的值為p1的話,則將其設置為p2。
最後,獲取ar對應的對象,並打印結果。p3.equals(p1)的結果為false,這是因為Person並沒有覆蓋equals()方法,而是采用繼承自Object.java的equals()方法;而Object.java中的equals()實際上是調用"=="去比較兩個對象,即比較兩個對象的地址是否相等。

Java多線程系列---“JUC原子類”05之 AtomicReference原子類