中文字幕av专区_日韩电影在线播放_精品国产精品久久一区免费式_av在线免费观看网站

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

Java對象結構與對象鎖的示例分析

發布時間:2022-03-02 12:33:28 來源:億速云 閱讀:143 作者:小新 欄目:開發技術

這篇文章主要介紹Java對象結構與對象鎖的示例分析,文中介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們一定要看完!

1. Java對象結構

Java對象結構包括三部分:對象頭、對象體和填充字節,如圖所示:

Java對象結構與對象鎖的示例分析

對象頭又包括三個字段:

  • 第一個字段叫作Mark Word(標記字),用于存儲自身運行時的數據,例如GC標志位、哈希碼、鎖狀態等信息。

  • 第二個字段叫作Class Pointer(類對象指針),用于存放方法區Class對象的地址,虛擬機通過這個指針來確定這個對象是哪個類的實例。

  • 第三個字段叫作Array Length(數組長度)。如果對象是一個Java數組,那么此字段必須有,用于記錄數組長度的數據;如果對象不是一個Java數組,那么此字段不存在,所以這是一個可選字段。

在32位JVM虛擬機中,Mark Word和Class Pointer這兩部分都是32位的;在64位JVM虛擬機中,Mark Word和Class Pointer這兩部分都是64位的。而我們需要重點理解的時mark word , 因為它跟synchronized的底層原理有關。

2. Mark Word的結構信息

Java內置鎖的狀態總共有4種,級別由低到高依次為:無鎖、偏向鎖、輕量級鎖和重量級鎖。其實在JDK 1.6之前,Java內置鎖還是一個重量級鎖,是一個效率比較低下的鎖,在JDK 1.6之后,JVM為了提高鎖的獲取與釋放效率,對synchronized的實現進行了優化,引入了偏向鎖和輕量級鎖,從此以后Java內置鎖的狀態就有了4種,并且4種狀態會隨著競爭的情況逐漸升級,而且是不可逆的過程,即不可降級,也就是說只能進行鎖升級。

1、不同鎖狀態下的Mark Word字段結構:

Mark Word字段的結構與Java內置鎖的狀態強相關。為了讓Mark Word字段存儲更多的信息,JVM將Mark Word最低兩個位設置為Java內置鎖狀態位,不同鎖狀態下的32位Mark Word結構如表所示:

Java對象結構與對象鎖的示例分析

64位的Mark Word與32位的Mark Word結構相似,結構如表所示:

Java對象結構與對象鎖的示例分析

2、64位Mark Word的介紹:

由于目前主流的JVM都是64位,因此我們使用64位的Mark Word。接下來對64位的Mark Word中各部分的內容進行具體介紹。

(1) lock:鎖狀態標記位,占兩個二進制位,由于希望用盡可能少的二進制位表示盡可能多的信息,因此設置了lock標記。該標記的值不同,整個Mark Word表示的含義就不同。

(2) biased_lock:對象是否啟用偏向鎖標記,只占1個二進制位。為1時表示對象啟用偏向鎖,為0時表示對象沒有偏向鎖。lock和biased_lock兩個標記位組合在一起共同表示Object實例處于什么樣的鎖狀態。二者組合的含義具體如表2-3所示。

lock和biased_lock兩個標記位組合在一起共同表示Object實例處于什么樣的鎖狀態。二者組合的含義具體如表所示:

Java對象結構與對象鎖的示例分析

(3) ptr_to_lock_record:占62位,在輕量級鎖的狀態下指向棧幀中鎖記錄的指針。

(4) ptr_to_heavyweight_monitor:占62位,在重量級鎖的狀態下指向對象監視器的指針。

3. 無鎖、偏向鎖、輕量級鎖和重量級鎖

在JDK 1.6版本之前,所有的Java內置鎖都是重量級鎖。重量級鎖會造成CPU在用戶態和核心態之間頻繁切換,所以代價高、效率低。JDK 1.6版本為了減少獲得鎖和釋放鎖所帶來的性能消耗,引入了偏向鎖和輕量級鎖的實現。所以,在JDK 1.6版本中內置鎖一共有4種狀態:無鎖狀態、偏向鎖狀態、輕量級鎖狀態和重量級鎖狀態,這些狀態隨著競爭情況逐漸升級。內置鎖可以升級但不能降級,意味著偏向鎖升級成輕量級鎖后不能再降級成偏向鎖。這種能升級卻不能降級的策略,其目的是提高獲得鎖和釋放鎖的效率。

(1) 無鎖狀態 :

Java對象剛創建時還沒有任何線程來競爭,說明該對象處于無鎖狀態(無線程競爭它),這時偏向鎖標識位是0,鎖狀態是01;

(2) 偏向鎖狀態:

偏向鎖是指一段同步代碼一直被同一個線程所訪問,那么該線程會自動獲取鎖,降低獲取鎖的代價。如果內置鎖處于偏向狀態,當有一個線程來競爭鎖時,先用偏向鎖,表示內置鎖偏愛這個線程,這個線程要執行該鎖關聯的同步代碼時,不需要再做任何檢查和切換。偏向鎖在競爭不激烈的情況下效率非常高。

偏向鎖狀態的Mark Word會記錄內置鎖自己偏愛的線程ID,內置鎖會將該線程當作自己的熟人,這時偏向鎖標識位是1,鎖狀態是01;

(3) 輕量級鎖狀態:

當有兩個線程開始競爭這個鎖對象時,情況就發生變化了,不再是偏向(獨占)鎖了,鎖會升級為輕量級鎖,兩個線程公平競爭,哪個線程先占有鎖對象,鎖對象的Mark Word就指向哪個線程的棧幀中的鎖記錄。這時偏向鎖標識位是0,鎖狀態是00;

當鎖處于偏向鎖,又被另一個線程企圖搶占時,偏向鎖就會升級為輕量級鎖。企圖搶占的線程會通過自旋的形式嘗試獲取鎖,不會阻塞搶鎖線程,以便提高性能。

自旋原理非常簡單,如果持有鎖的線程能在很短時間內釋放鎖資源,那么那些等待競爭鎖的線程就不需要進行內核態和用戶態之間的切換來進入阻塞掛起狀態,它們只需要等一等(自旋),等持有鎖的線程釋放鎖后即可立即獲取鎖,這樣就避免了用戶線程和內核切換的消耗。

但是,線程自旋是需要消耗CPU的,如果一直獲取不到鎖,那么線程也不能一直占用CPU自旋做無用功,所以需要設定一個自旋等待的最大時間。JVM對于自旋周期的選擇,JDK 1.6之后引入了適應性自旋鎖,適應性自旋鎖意味著自旋的時間不是固定的,而是由前一次在同一個鎖上的自旋時間以及鎖的擁有者的狀態來決定的。線程如果自旋成功了,下次自旋的次數就會更多,如果自旋失敗了,自旋的次數就會減少。

如果持有鎖的線程執行的時間超過自旋等待的最大時間仍沒有釋放鎖,就會導致其他爭用鎖的線程在最大等待時間內還是獲取不到鎖,自旋不會一直持續下去,這時爭用線程會停止自旋進入阻塞狀態,該鎖膨脹為重量級鎖。

(4) 重量級鎖狀態:

重量級鎖會讓其他申請的線程之間進入阻塞,性能降低。重量級鎖也叫同步鎖,這個鎖對象MarkWord再次發生變化,會指向一個監視器對象,該監視器對象用集合的形式來登記和管理排隊的線程。這時偏向鎖標識位是0,鎖狀態是10;

以上是“Java對象結構與對象鎖的示例分析”這篇文章的所有內容,感謝各位的閱讀!希望分享的內容對大家有幫助,更多相關知識,歡迎關注億速云行業資訊頻道!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

虎林市| 云南省| 荥经县| 盘山县| 小金县| 泾源县| 两当县| 临沧市| 永川市| 池州市| 顺义区| 宁强县| 泉州市| 连南| 沅江市| 邢台县| 岗巴县| 昌乐县| 天长市| 渝中区| 旌德县| 云梦县| 华池县| 蒙城县| 连云港市| 南部县| 华蓥市| 平凉市| 正宁县| 丹巴县| 松潘县| 平南县| 樟树市| 金湖县| 运城市| 肃北| 潞城市| 刚察县| 旺苍县| 勃利县| 榆中县|