個(gè)人梳理總結(jié):
一.synchornized原理
? ?1. synchornized內(nèi)置鎖是一種對(duì)象鎖(鎖的是對(duì)象而非引用),作用粒度是對(duì)象,可以用來實(shí)現(xiàn)臨界資源的同步互斥訪問,是可重入的.
????2.synchornized屬于隱式鎖,是jvm內(nèi)置鎖,jvm會(huì)自動(dòng)加鎖跟解鎖,由于他是對(duì)象鎖,所以他不夠靈活,不能跨方法加鎖,
如果要實(shí)現(xiàn)跨方法加鎖,有兩種方式:
????????????????????????????????????????????1.ReentrantLock(顯示鎖)進(jìn)行手動(dòng)加鎖和手動(dòng)解鎖
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?2.使用魔術(shù)類unsafe直接越過jvm,去操作底層對(duì)對(duì)象進(jìn)行手動(dòng)加鎖和解鎖
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?UnsafeInstance.reflectGetUnsafe().mintorEnter(object)? //加鎖
? ?????????????????????????????????????????????????????????UnsafeInstance.reflectGetUnsafe().mintorExit(object)? //解鎖
? ? 3.synchornized底層原理:每個(gè)對(duì)象在創(chuàng)建的時(shí)候都會(huì)創(chuàng)建一個(gè)與之對(duì)應(yīng)的Moniter對(duì)象,基于進(jìn)入與退出Moniter對(duì)象實(shí)現(xiàn)方法與代碼塊同步,Moniter底層就是一個(gè)Mutex Lock(互斥鎖),它是一個(gè)重量級(jí)鎖,性能低,但是在1.5版本后對(duì)其做出了重大優(yōu)化,如鎖粗化、鎖消除(Lock Elimination)、輕量級(jí)鎖(Lightweight Locking)、偏向鎖(Biased Locking)、適應(yīng)性自旋(Adaptive Spinning)等技術(shù)來減少鎖操作的開銷,內(nèi)置鎖的并發(fā)性能已經(jīng)基本與Lock持平

? ? 4.每個(gè)對(duì)象在加鎖以后,會(huì)在對(duì)象的對(duì)象頭中記錄鎖的狀態(tài),對(duì)象信息,鎖的狀態(tài)標(biāo)志,偏向鎖ID,偏向時(shí)間,
二.Jvm鎖的優(yōu)化
? ? ? ? ?1.鎖的粗化
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? ? StringBuffer stb = new StringBuffer();?
? ? ? ? ? ? ? ? ? ?stb.append("桑");
? ? ? ? ? ? ? ? ? ? stb.append("翔");
? ? ? ? 2.鎖的消除
? synchornized(new Object){
? ? ? ? ? ? //偽代碼:很多邏輯
????????}
三.JVM內(nèi)置鎖的膨脹升級(jí)
? ? ? ? 下面的過程是不可逆的
? ? ? ??
? ? ? ? 1.偏向鎖:jvm認(rèn)為當(dāng)進(jìn)入同步塊的時(shí)候一幫認(rèn)為只有一個(gè)線程,那么鎖就會(huì)進(jìn)入偏向模式,當(dāng)這個(gè)線程再次請(qǐng)求鎖的時(shí)候,無(wú)需再做任何同步操作,提高了性能
? ? ? ? 2.輕量級(jí)鎖:在鎖競(jìng)爭(zhēng)比較激烈的場(chǎng)合,偏向鎖就失效,升級(jí)成為了輕量級(jí)鎖,它的場(chǎng)合一般是線程交替執(zhí)行同步塊的場(chǎng)合(競(jìng)爭(zhēng)不是很激烈),當(dāng)?shù)诙€(gè)線程來競(jìng)爭(zhēng)鎖的時(shí)候,不會(huì)讓其阻塞,而是進(jìn)行自旋,這樣就不會(huì)丟棄CPU的使用權(quán),減少喚醒阻塞線程的開銷
? ? ? ? 3.輕量級(jí)鎖是如何記錄當(dāng)前交替執(zhí)行的線程的呢?
? ? ? ? ? ?當(dāng)鎖升級(jí)成輕量級(jí)鎖的時(shí)候,線程會(huì)在自己的線程棧中開辟一個(gè)LockRecord空間,將此對(duì)象頭中的信息復(fù)制一份放入當(dāng)中,并且將原對(duì)象頭中的信息指向線程棧中的owner指針

? ??????????

? ? ? ?鎖定膨脹實(shí)際過程:
? ? ? ? ? ? Mark Word

? ? ? 1.??
? ? ? ? 解析:當(dāng)一個(gè)線程訪問同步塊的時(shí)候,他會(huì)先檢查同步對(duì)象的標(biāo)志位,就是上圖中的鎖標(biāo)志位為01,和是否偏向0

此時(shí)就會(huì)通過CAS修改成是否偏向1,獲取偏向鎖,并將MarkWord中的線程ID指向自己

然后執(zhí)行同步塊中的邏輯,? ? 此時(shí)如果又有一個(gè)線程訪問同步塊,同樣會(huì)檢查標(biāo)志位中的信息,并會(huì)嘗試修改MarkWord中的線程ID,此時(shí)會(huì)修改失敗,當(dāng)?shù)谝粋€(gè)線程運(yùn)行到一個(gè)安全位置以后,若第一個(gè)線程沒有運(yùn)行完畢,則會(huì)升級(jí)為輕量級(jí)鎖,讓第二個(gè)線程自旋等待,如果第一個(gè)線程執(zhí)行完畢,則降偏向1改為0,線程id清空;
:

2.

四.ReentrantLock&AQS

1.概念:? Java并發(fā)編程核心在于java.concurrent.util包而juc當(dāng)中的大多數(shù)同步器
實(shí)現(xiàn)都是圍繞著共同的基礎(chǔ)行為,比如等待隊(duì)列、條件隊(duì)列、獨(dú)占獲取、共享獲
取等,而這個(gè)行為的抽象就是基于AbstractQueuedSynchronizer簡(jiǎn)稱AQS,AQS定
義了一套多線程訪問共享資源的同步器框架,是一個(gè)依賴狀態(tài)(state)的同步器
?2.應(yīng)用:Lock,Latch,Barrier,線程池中的阻塞隊(duì)列等都是基于AQS去實(shí)現(xiàn)的
3.AQS框架管理狀態(tài):
? ? ? ? 1.? state表示資源的可用狀態(tài)(用volitel修飾的,保證線程的可見性)
? ? ? ? ? ? ? ? 通過CAS操作去原子性的操作state值(底層是unsafe類操作匯編指令)
? ? ? ? ?2. node(CLH同步隊(duì)列---阻塞)
? ? ? ? ? ? ? ? 用來存放沒有獲取競(jìng)爭(zhēng)鎖的線程,內(nèi)部有各種標(biāo)記當(dāng)前節(jié)點(diǎn)的信號(hào)量屬性,前后繼節(jié)點(diǎn)等
? ??????


? ? ? ? 3.exclusiveOwnerThread,表示當(dāng)前獨(dú)占線程是誰(shuí)------源自AbstractOwnableSynchronizer(AbstractQueuedSynchronizer繼承的)
當(dāng)有一個(gè)線程進(jìn)行加鎖的時(shí)候:

? ? ?head和tail都為null,表示CHL隊(duì)列中沒有等待的線程
當(dāng)有二個(gè)線程進(jìn)行加鎖的時(shí)候? ? ? ?

? ??????
? ??????????