- CAS:首先CPU將內存中的將要被修改的數據與預期的值進行比較,如果這兩個值相等,CPU則會將內存中數值替換爲新值,否則不做操作。
-
Synchronized原理:
_EntryList、Owner、_WaitSet【1】:進入獲取鎖的線程、指向持有Monitor對象的線程、等待獲取鎖的線程
tip1【2】:對象的內存佈局:對象頭,實例數據,對齊填充(對齊填充並不是必然存在的,僅僅起着佔位符的作用,保證對象頭部分正好是8字節的倍數。)
偏向鎖【3】:無實際競爭,且將來只有第一個申請鎖的線程會使用鎖。
輕量級鎖【3】:無實際競爭,多個線程交替使用鎖;允許短時間的鎖競爭。
重量級鎖:的加鎖、解鎖過程和輕量級鎖差不多,區別是:競爭失敗後,線程阻塞,釋放鎖後,喚醒阻塞的線程
- AQS【4】:AbustactQueuedSynchronizer的簡稱,它是一個Java提高的底層同步工具類,用一個int類型的變量表示同步狀態,並提供了一系列的CAS操作來管理這個同步狀態。
同步隊列是AQS很重要的組成部分,它是一個雙端隊列,遵循FIFO原則,主要作用是用來存放在鎖上阻塞的線程,當一個線程嘗試獲取鎖時,如果已經被佔用,那麼當前線程就會被構造成一個Node節點假如到同步隊列的尾部,隊列的頭節點是成功獲取鎖的節點,當頭節點線程是否鎖時,會喚醒後面的節點並釋放當前頭節點的引用。
獨佔鎖和共享鎖:獨佔鎖的同步狀態值爲1,即同一時刻只能有一個線程成功獲取同步狀態;共享鎖的同步狀態>1,取值由上層同步組件確定。
重入鎖:基本原理是判斷上次獲取鎖的線程是否爲當前線程,如果是則可再次進入臨界區,如果不是,則阻塞。
- LongAccumulator:LongAccumulator相比於LongAdder可以提供累加器初始非0值,後者只能默認爲0,另外前者還可以指定累加規則比如不是累加而是相乘,只需要構造LongAccumulator時候傳入自定義雙面運算器就OK,後者則內置累加的規則。
- blockqueue:線程共享通道,當有新的消息進入隊列後,自動將線程喚醒。例子【5】
- 臨界資源:是一次僅允許一個進程使用的共享資源; 臨界區:每個進程中訪問臨界資源的那段代碼稱爲臨界區,每次只允許一個進程進入臨界區,進入後,不允許其他進程進入。
- synchronized,lock比較:
(1)來源: lock是一個接口,而synchronized是java的一個關鍵字,synchronized是內置的語言實現;
(2)異常是否釋放鎖: synchronized在發生異常時候會自動釋放佔有的鎖,因此不會出現死鎖;而lock發生異常時候,不會主動釋放佔有的鎖,必須手動unlock來釋放鎖,可能引起死鎖的發生。(所以最好將同步代碼塊用try catch包起來,finally中寫入unlock,避免死鎖的發生。)
(3)是否響應中斷 :lock等待鎖過程中可以用interrupt來中斷等待,而synchronized只能等待鎖的釋放,不能響應中斷;
(4)是否知道獲取鎖 :Lock可以通過trylock來知道有沒有獲取鎖,而synchronized不能;
(5)Lock可以提高多個線程進行讀操作的效率。(可以通過readwritelock實現讀寫分離)
在性能上來說,如果競爭資源不激烈,兩者的性能是差不多的,而當競爭資源非常激烈時(即有大量線程同時競爭),此時Lock的性能要遠遠優於synchronized。所以說,在具體使用時要根據適當情況選擇。
(6)synchronized使用Object對象本身的wait 、notify、notifyAll調度機制,而Lock可以使用Condition進行線程之間的調度。
(7)synchronized原始採用的是CPU悲觀鎖機制,即線程獲得的是獨佔鎖。而Lock用的是樂觀鎖方式。
- lock使用場景:
1.某個線程在等待一個鎖的控制權的這段時間需要中斷
2.需要分開處理一些wait-notify,ReentrantLock裏面的Condition應用,能夠控制notify哪個線程
3.具有公平鎖功能,每個到來的線程都將排隊等候
- ReentrantLock實現原理:【7】
- 徹底理解ThreadLocal:【8】
-
Java 9 Reactive Streams【9】:取消訂閱可能會導致主線程邏輯死循環、當發佈者以比訂閱者消費更快的速度生成消息時,會產生背壓
-
Java實現生產者-消費者模型【10】:
1、BlockingQueue
2、wait && notify
3、簡單的Lock && Condition(高級:生產、消費鎖分離,以此讓優化消費者與消費者(或生產者與生產者)之間是串行的;消費者與生產者之間是並行的,buffer在頭部出隊,尾部入隊)
4、Semaphore
-
線程池的處理流程和原理:
- Synchronized與ReentrantLock有什麼不同,各適用什麼場景:在確實需要一些 synchronized 所沒有的特性的時候,比如時間鎖等候、可中斷鎖等候、無塊結構鎖、多個條件變量或者輪詢鎖。
- ReentrantReadWriteLock實現原理【13】:表示兩個鎖,一個是讀操作相關的鎖,稱爲共享鎖;一個是寫相關的鎖,稱爲排他鎖
【1】https://www.cnblogs.com/monkey0307/p/9667606.html 《JAVA對象內存結構》
【2】https://blog.csdn.net/u010126792/article/details/82968521 《JVM學習之對象內存佈局,對象頭》
【3】https://www.jianshu.com/p/36eedeb3f912 《淺談偏向鎖、輕量級鎖、重量級鎖》
【4】https://blog.csdn.net/zhangdong2012/article/details/79983404 《Java併發-AQS及各種Lock鎖的原理》
【5】https://www.jianshu.com/p/024a36b83099 《併發編程-BlockQueue線程容器》
【6】https://blog.csdn.net/tingfeng96/article/details/52219649 《synchronized 和Lock區別》
【7】https://www.jianshu.com/p/b6efbdbdc6fa 《ReentrantLock實現機制(CLH隊列鎖)》
【8】https://www.cnblogs.com/xzwblog/p/7227509.html 《徹底理解ThreadLocal》
【9】https://blog.csdn.net/why_still_confused/article/details/82351960 《Java 9 Reactive Streams》
【10】https://www.jianshu.com/p/3d4cbb969063 《Java實現生產者-消費者模型》
【11】https://www.jianshu.com/p/519803f392dc 《線程池的處理流程和原理》
【12】https://www.ibm.com/developerworks/cn/java/j-jtp10264/index.html 《JDK 5.0 中更靈活、更具可伸縮性的鎖定機制》
【13】https://www.cnblogs.com/faunjoe88/p/7928757.html 《輕鬆掌握java讀寫鎖(ReentrantReadWriteLock)的實現原理》