Java併發——鎖框架(三)讀寫鎖
1. 讀寫鎖機制——ReadWriteLock介面
讀寫鎖適用於對資料結構頻繁讀而較少修改的場景。舉個栗子,你可以建立一個線上詞典供多條讀執行緒併發讀取,然而單條寫執行緒可能會不時新增新的定義或更新已有的定義。一個資源可以被多個執行緒同時讀,或者被一個執行緒寫,但是不能同時存在讀和寫執行緒。
基本規則: 讀讀不互斥 、讀寫互斥 、寫寫互斥。
問:既然讀讀不互斥,為什麼還要加讀鎖?
答:如果讀可以不是最新資料,也不需要加鎖。要保證讀取資料的嚴格實時性,就必須加讀寫鎖。
2. ReadWriteLock介面宣告的方法
(1)Lock readLock():返回用於讀的鎖。
(2)Lock writeLock():返回用於寫的鎖。
3. ReadWriteLock介面的實現類——重入讀寫鎖ReentrantReadWriteLock
常用方法
方法名稱 | 描述 |
ReentrantReadWriteLock() | 建立一個重入讀寫鎖的例項。 |
ReentrantReadWriteLock(boolean fair) | 建立一個具有公平策略的重入讀寫鎖例項。 |
ReadLock readLock() | 返回用於讀的鎖。 |
WriteLock writeLock() | 返回用於寫的鎖。 |
int getReadHoldCount() | 返回被呼叫執行緒在這個鎖上持有讀鎖的數量,當呼叫執行緒沒有持有這個讀鎖,返回0. |
int getWriteHoldCount() | 返回被呼叫執行緒在這個鎖上持有寫鎖的數量,當呼叫執行緒沒有持有這個寫鎖,返回0. |
4. 示例
寫執行緒產生單詞定義的條目,而讀執行緒持續隨機地訪問這些條目並打印出來。
import java.util.HashMap; import java.util.Map; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReadWriteLock; import java.util.concurrent.locks.ReentrantReadWriteLock; public class ReentrantReadWriteLockDemo { public static void main(String[] args) { final String[] words = {"dog","cat","bird","fish","human"}; final String[] definitions = {"a member of the genus Canis", "feline mammal usually having thick soft fur ", "A bird is a feathered, winged, bipedal, warm-blooded, egg-laying, vertebrate animal.", "Fish are vertebrates with gills that live in water", "characterized by superior intelligence, articulate speech, and erect carriage"}; final Map<String,String> dictionary = new HashMap<String,String>(); ReadWriteLock rwlock = new ReentrantReadWriteLock(); final Lock rlock = rwlock.readLock(); final Lock wlock = rwlock.writeLock(); Runnable writer = ()-> { for(int i = 0; i < words.length; i++) { wlock.lock(); dictionary.put(words[i], definitions[i]); System.out.println("寫入單詞:"+words[i]); wlock.unlock(); try { Thread.sleep(100); //讓其他執行緒有機會執行 } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } }; ExecutorService es = Executors.newFixedThreadPool(1); es.submit(writer); Runnable reader = ()-> { while(true) { rlock.lock(); int i = (int) (Math.random() * words.length); //隨機讀取一個單詞 System.out.println("讀取單詞:"+words[i]+",它的意思是:" + dictionary.get(words[i])); rlock.unlock(); } }; es = Executors.newFixedThreadPool(1); es.submit(reader); } }
執行結果:
讀取單詞:human,它的意思是:characterized by superior intelligence, articulate speech, and erect carriage
讀取單詞:cat,它的意思是:feline mammal usually having thick soft fur
讀取單詞:fish,它的意思是:Fish are vertebrates with gills that live in water
讀取單詞:dog,它的意思是:a member of the genus Canis
讀取單詞:fish,它的意思是:Fish are vertebrates with gills that live in water
讀取單詞:cat,它的意思是:feline mammal usually having thick soft fur
讀取單詞:fish,它的意思是:Fish are vertebrates with gills that live in water
讀取單詞:cat,它的意思是:feline mammal usually having thick soft fur........