最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

分析JVM的執(zhí)行子系統(tǒng)

 更新時間:2021年06月23日 10:28:48   作者:IT王小二  
本文主要介紹了JVM執(zhí)行子系統(tǒng)。了解虛擬機是如何執(zhí)行程序的, 虛擬機怎樣運行一個Class文件的概念模型, 可以更好的理解怎樣寫出優(yōu)秀的代碼

一、Class類文件結構

1.1、JVM的平臺無關性

與平臺無關性是建立在操作系統(tǒng)上,虛擬機廠商提供了許多可以運行在各種不同平臺的虛擬機,它們都可以載入和執(zhí)行字節(jié)碼,從而實現(xiàn)程序的一次編寫,到處運行。

各種不同平臺的虛擬機與所有平臺都統(tǒng)一使用的程序存儲格式——字節(jié)碼(ByteCode)是構成平臺無關性的基石,也是語言無關性的基礎。Java 虛擬機不和包括 Java 在內(nèi)的任何語言綁定,它只與“Class 文件”這種特定的二進制文件格式所關聯(lián),Class 文件中包含了 Java 虛擬機指令集和符號表以及若干其他輔助信息。

1.2、Class類文件

  • Class文件是一組以8位字節(jié)為基礎單位的二進制流。
  • 類似于結構體的偽結構來存儲數(shù)據(jù)。
  • 只有兩種數(shù)據(jù)類型:無符號數(shù)和表。
  • 無符號數(shù)屬于基本的數(shù)據(jù)類型,以u1、u2、u4、u8 。
  • 表是由多個無符號數(shù)或者其他表作為數(shù)據(jù)項構成的復合數(shù)據(jù)類型。

其中值得注意的一個東西,class文件中有顯示編譯的版本號,使用notepad++等工具打開class文件。

圖中標記前四個被稱為魔數(shù)(唯一作用是確定這個文件是否為一個能被虛擬機接受的 Class 文件)。

后兩個標記代表class文件的版本號,其中第4第500 00字節(jié)代表著jdk的次版本號,第6第7個字節(jié)00 34代表這jdk的主版本號,Java 的版本號是從 45 開始的,JDK 1.1 之后的每個 JDK 大版本發(fā)布主版本號向上加 1 高版本的 JDK 能向下兼容以前版本的 Class 文件,但不能運行以后版本的 Class 文件,即使文件格式并未發(fā)生任何變化,虛擬機也必須拒絕執(zhí)行超過其版本號的 Class 文件。

34為16進制,轉(zhuǎn)化為10進制就是52,所以 52-45+1 , 代表這個class文件的版本號為jdk1.8 。

當然class文件的結構詳細說起來還有常量池、訪問標志、父索引、接口索引、字段表集合、方法表集合、屬性表集合,這些以后有時間再補上吧,概念性東西,對實際開發(fā)代碼,優(yōu)化代碼幫助不大。

二、類的加載機制

類從被加載到虛擬機內(nèi)存中開始,到卸載出內(nèi)存為止,它的整個生命周期包括:加載(Loading)、驗證(Verification)、準備(Preparation)、解析(Resolution)、初始化(Initialization)、使用(Using)和卸載(Unloading)7 個階段。其中驗證、準備、解析 3 個部分統(tǒng)稱為連接(Linking)。

2.1、加載

虛擬機需要完成以下 3 件事情:

1、通過一個類的全限定名來獲取定義此類的二進制字節(jié)流。

2、將這個字節(jié)流所代表的靜態(tài)存儲結構轉(zhuǎn)化為方法區(qū)的運行時數(shù)據(jù)結構。

3、在內(nèi)存中生成一個代表這個類的 java.lang.Class 對象,作為方法區(qū)這個類的各種數(shù)據(jù)的訪問入口。

2.2、驗證

是連接階段的第一步,這一階段的目的是為了確保 Class 文件的字節(jié)流中包含的信息符合當前虛擬機的要求,并且不會危害虛擬機自身的安全。但從整體上看,驗證階段大致上會完成下面 4 個階段的檢驗動作:文件格式驗證、元數(shù)據(jù)驗證、字節(jié)碼驗證、符號引用驗證。

2.3、準備階段

為類變量分配內(nèi)存并設置類變量初始值(零值)的階段。

2.4、解析階段

是虛擬機將常量池內(nèi)的符號引用替換為直接引用的過程。

2.5、初始化階段

是類加載過程的最后一步,前面的類加載過程中,除了在加載階段用戶應用程序可以通過自定義類加載器參與之外,其余動作完全由虛擬機主導和控制。

到了初始化階段,才真正開始執(zhí)行類中定義的 Java 程序代碼在準備階段,變量已經(jīng)賦過一次系統(tǒng)要求的初始值,而在初始化階段,則根據(jù)程序員通過程。

序制定的主觀計劃去初始化類變量和其他資源(即調(diào)用類構造器之類的)。

5種情況會對類立即進行初始化(了解即可)

1、遇到 new、getstatic、putstatic 或 invokestatic 這 4 條字節(jié)碼指令時,如果類沒有進行過初始化,則需要先觸發(fā)其初始化。生成這 4 條指令的最常見的Java 代碼場景是:使用 new 關鍵字實例化對象的時候、讀取或設置一個類的靜態(tài)字段(被 final 修飾、已在編譯期把結果放入常量池的靜態(tài)字段除外)的時候,以及調(diào)用一個類的靜態(tài)方法的時候。

2、使用 java.lang.reflect 包的方法對類進行反射調(diào)用的時候,如果類沒有進行過初始化,則需要先觸發(fā)其初始化。

3、當初始化一個類的時候,如果發(fā)現(xiàn)其父類還沒有進行過初始化,則需要先觸發(fā)其父類的初始化。

4、當虛擬機啟動時,用戶需要指定一個要執(zhí)行的主類(包含 main()方法的那個類),虛擬機會先初始化這個主類。

5、當使用 JDK 1.7 的動態(tài)語言支持時,如果一個 java.lang.invoke.MethodHandle 實例最后的解析結果 REF_getStatic、REF_putStatic、REF_invokeStatic 的方法句柄,并且這個方法句柄所對應的類沒有進行過初始化,則需要先觸發(fā)其初始化。

三、類加載器

對于任意一個類,都需要由 加載它的類加載器和這個類本身一同確立其在 Java 虛擬機中的唯一性 ,每一個類加載器,都擁有一個獨立的類名稱空間。這句話可以表達得更通俗一些:比較兩個類是否“相等”,只有在這兩個類是由同一個類加載器加載的前提下才有意義,否則,即使這兩個類來源于同一個 Class 文件,被同一個虛擬機加載,只要加載它們的類加載器不同,那這兩個類就必定不相等。這里所指的“相等”,包括代表類的 Class 對象的 equals()方法、isAssignableFrom()方法、isInstance()方法的返回結果,也包括使用 instanceof 關鍵字做對象所屬關系判定等情況。

3.1、雙親委派模型

  • 啟動類加載器 : BootstrapClassLoader,負責加載存放在JDK\jre\lib(JDK代表JDK的安裝目錄,下同)下,或被 -Xbootclasspath參數(shù)指定的路徑中的,并且能被虛擬機識別的類庫(如rt.jar,所有的java.開頭的類均被 BootstrapClassLoader加載)。啟動類加載器是無法被Java程序直接引用的。
  • 擴展類加載器 : ExtensionClassLoader,該加載器由sun.misc.Launcher$ExtClassLoader實現(xiàn),它負責加載 JDK\jre\lib\ext目錄中,或者由java.ext.dirs系統(tǒng)變量指定的路徑中的所有類庫(如javax.開頭的類),開發(fā)者可以直接使用擴展類加載器。
  • 應用類加載器 : ApplicationClassLoader,該類加載器由 sun.misc.Launcher$AppClassLoader來實現(xiàn),它負責加載用戶類路徑(ClassPath)所指定的類,開發(fā)者可以直接使用該類加載器,如果應用程序中沒有自定義過自己的類加載器,一般情況下這個就是程序中默認的類加載器。
  • 自定義ClassLoader :在自定義 ClassLoader 的子類時候,我們常見的會有兩種做法,一種是重寫 loadClass 方法,另一種是重寫 findClass 方法。其實這兩種方法本質(zhì)上差不多畢竟 loadClass 也會調(diào)用 findClass,但是從邏輯上講我們最好不要直接修改 loadClass 的內(nèi)部邏輯。建議的做法是只在 findClass 里重寫自定義類的加載方法。loadClass 這個方法是實現(xiàn)雙親委托模型邏輯的地方,擅自修改這個方法會導致模型被破壞,容易造成問題。因此我們最好是在雙親委托模型框架內(nèi)進行小范圍的改動,不破壞原有的穩(wěn)定結構。同時,也避免了自己重寫 loadClass 方法的過程中必須寫雙親委托的重復代碼,從代碼的復用性來看,不直接修改這個方法始終是比較好的選擇。

雙親委派模型的過程:

1、當 AppClassLoader加載一個class時,它首先不會自己去嘗試加載這個類,而是把類加載請求委派給父類加載器ExtClassLoader去完成。

2、當 ExtClassLoader加載一個class時,它首先也不會自己去嘗試加載這個類,而是把類加載請求委派給BootStrapClassLoader去完成。

3、如果 BootStrapClassLoader加載失敗(例如在 $JAVA_HOME/jre/lib里未查找到該class),會使用 ExtClassLoader來嘗試加載。

4、若ExtClassLoader也加載失敗,則會使用 AppClassLoader來加載,如果 AppClassLoader也加載失敗,則會報出異常 ClassNotFoundException。

雙親委派模型的好處:

Java類隨著它的類加載器一起具備了帶有優(yōu)先級的層次關系,保證java程序穩(wěn)定運行。

3.2、Tomcat是怎么保證兩個應用相同名稱類的隔離性

tomcat下可能會同時部署多個應用,那么tomcat是怎么保證多個應用相同類(比如 SysUserService 類)呢?

  • Tomcat 本身也是一個 java 項目,因此其也需要被 JDK 的類加載機制加載,也就必然存在啟動類加載器、擴展類加載器和應用系統(tǒng)類加載器。
  • 為了保證多應用相同類的唯一性,tomcat在一定程度上打破了雙親委派模型,每啟動一個項目都會創(chuàng)建一個唯一的WebApp類加載器,分別用來加載不同的應用,所以就保證了類的唯一性。

以上就是分析JVM的執(zhí)行子系統(tǒng)的詳細內(nèi)容,更多關于JVM 執(zhí)行子系統(tǒng)的資料請關注腳本之家其它相關文章!

相關文章

  • Spring面向切面編程AOP詳情

    Spring面向切面編程AOP詳情

    這篇文章主要介紹了Spring面向切面編程AOP詳情,文章圍繞主題展開詳細的內(nèi)容介紹,具有一定的參考價值,需要的小伙伴可以參考一下
    2022-09-09
  • Spring@Autowired與@Resource的區(qū)別有哪些

    Spring@Autowired與@Resource的區(qū)別有哪些

    這篇文章主要為大家詳細介紹了@Autowired與@Resource的區(qū)別,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下,希望能夠給你帶來幫助
    2022-02-02
  • 詳解JAVA 連等賦值問題

    詳解JAVA 連等賦值問題

    這篇文章主要介紹了JAVA 連等賦值問題,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2019-03-03
  • Java冒泡排序簡單實現(xiàn)

    Java冒泡排序簡單實現(xiàn)

    這篇文章主要介紹了Java冒泡排序簡單實現(xiàn),具有一定借鑒價值,需要的朋友可以參考下。
    2017-12-12
  • 詳解手把手Maven搭建SpringMVC+Spring+MyBatis框架(超級詳細版)

    詳解手把手Maven搭建SpringMVC+Spring+MyBatis框架(超級詳細版)

    本篇文章主要介紹了手把手Maven搭建SpringMVC+Spring+MyBatis框架(超級詳細版),具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2017-12-12
  • Idea2023配置tomcat服務器的圖文教程

    Idea2023配置tomcat服務器的圖文教程

    這篇文章主要介紹了Idea2023配置tomcat服務器的圖文教程,本文是javaweb新手版教程,IDEA2023+JDK1.8+apache-tomcat-8.5.91,沒有使用Maven,需要的朋友可以參考下
    2023-10-10
  • SpringBoot整合SpringTask實現(xiàn)定時任務的流程

    SpringBoot整合SpringTask實現(xiàn)定時任務的流程

    這篇文章主要介紹了SpringBoot整合SpringTask實現(xiàn)定時任務的流程,本文給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2020-06-06
  • Java ApiPost請求返回406狀態(tài)碼問題的解決方案

    Java ApiPost請求返回406狀態(tài)碼問題的解決方案

    APIPost是一款專為開發(fā)者和測試人員設計的API測試工具,類似于Postman,但提供了更多的團隊協(xié)作和文檔管理功能,它可以幫助你更好地進行接口調(diào)試和集成測試,但遇到了請求后返回的是406狀態(tài),所以本文給大家介紹了Java ApiPost請求返回406狀態(tài)碼問題的解決方案
    2025-04-04
  • 5種Java中數(shù)組的拷貝方法總結分享

    5種Java中數(shù)組的拷貝方法總結分享

    這篇文章主要介紹了5種Java中數(shù)組的拷貝方法總結分享,文章圍繞主題展開詳細的內(nèi)容介紹,具有一定的參考價值,需要的朋友可以參考一下
    2022-07-07
  • 關于HashMap相同key累加value的問題

    關于HashMap相同key累加value的問題

    這篇文章主要介紹了關于HashMap相同key累加value的問題,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-05-05

最新評論

沁阳市| 电白县| 隆德县| 色达县| 许昌市| 眉山市| 滦平县| 绥宁县| 桂阳县| 沈丘县| 诏安县| 健康| 玉龙| 孟村| 太仆寺旗| 珲春市| 江安县| 上栗县| 武胜县| 邢台市| 搜索| 甘洛县| 金溪县| 万荣县| 易门县| 东兰县| 杨浦区| 宜都市| 辽源市| 普宁市| 黄浦区| 远安县| 德保县| 图木舒克市| 吉安县| 镇巴县| 安福县| 义乌市| 平南县| 甘泉县| 枣强县|