顯示鎖和內(nèi)置鎖
? ? ? ? Synchronized屬于內(nèi)置鎖。Lock接口屬于顯示鎖。
Lock
????????Lock類是一個接口,核心方法有l(wèi)ock(),unLock(),tryLock()
synchronized和lock比較??
? ? ? ? synchronized會比lock消耗的性能會少一點。因為lock是一個類,使用時需要創(chuàng)建一個對象的實例。而lock又比synchronized使用起來更靈活。
Lock的兩個實現(xiàn)類
? ??????Lock接口有兩個實現(xiàn)用到的比較多:ReentrantLock(可重入鎖,默認是非公平鎖)和ReentrantReadWriteLock(讀寫鎖)
Lock使用范式
????try{
????????lock.Lock();
????????????//做業(yè)務邏輯
????????} finally{
????????????//解鎖
????????????lock.unlock();
????????}
可重入鎖
? ? ????不能鎖自己,比如遞歸調(diào)用時,可以繼續(xù)進入這把鎖。
所謂鎖的公平和非公平
? ? ? ? 公平就是競爭鎖的線程排隊等候獲取鎖,等待時間最長的線程先拿鎖,后來的排隊等候。非公平就是誰先搶到就是誰的(因為線程從等待到喚醒需要上下文切換的時間,而這時正好有新的線程來拿鎖,可能新來的線程先拿到)。Syn是非公平鎖。
? ??????公平鎖和非公平鎖其實不是由aqs來管的,是由實現(xiàn)這個鎖來管的。非公平鎖就是先嘗試搶一次,如果搶到了則獲取鎖。公平鎖是判斷當前隊列有沒有節(jié)點等待,如果有的話則放到隊列尾部等待。
讀寫鎖
? ? ? ? 創(chuàng)建讀寫鎖:ReentrantReadWriteLock是實現(xiàn)類,ReadWriteLock是接口,如果要創(chuàng)建的話應該是ReadWriteLock lock = new ReentrantReadWriteLock();
? ? ? ? 讀寫鎖的機制:寫獨占,讀共享,但是讀寫互斥。
? ??????ReentrantReadWriteLock:ReentrantReadWriteLock實現(xiàn)上,讀和寫用的是一把鎖,通過sync里的status值來記錄的,因為status是int型,32位,高(16-32)16位用來記錄讀鎖,低(0-16)16位用來記錄寫鎖,而可重入的讀鎖通過ThreadLocal來實現(xiàn)記錄重入次數(shù)。
Condition接口
? ??????類似于syn中用到的notify和wait方法。配合Lock使用。Signal()方法對應notify,await()方法對應wait方法。喚醒基本用signal,而不用signalAll。
LockSupport
? ??????LockSupport定義了一組的公共靜態(tài)方法,這些方法提供了最基本的線程阻塞和喚醒功能,park方法是阻塞線程,unPark(Thread thread)是喚醒線程。而LockSupport 也成為構建同步組件的基礎工具。
CLH
? ??????隊列鎖。每一個鎖都有兩個參數(shù),myPred和locked,locked等于當前線程使用鎖的情況,myPred是一個自旋規(guī)則,會不斷的向前面的線程查看locked值,當前面線程使用完鎖后,會把自己的locked置為false,本線線程就能使用該鎖了,當使用完再把自己的locked置為fasle,供后面的線程使用。
AQS(AbstractQueuedSynchronizer同步器)
? ??????同步器的設計基于模板方法模式。,定義一個操作中的算法的骨架,而將一些步驟的實現(xiàn)延遲到子類中。模板方法模式最常見的使用就是spring框架中的各種template。