类加载机制(整个过程详解)
一:背景
類加載機制是在我們的真個java的運行階段中的其中一個階段。
二:什么是快樂星球(類加載機制)
我們編寫的 Java 文件都是以.java 為后綴的文件,編譯器會將我們編寫的.java 的文件編譯成.class 文件,簡單來說類加載機制就是jvm從文件系統將一系列的 class 文件z轉化為二進制流加載 JVM 內存中并生成一個該類的Class對象,為后續程序運行提供資源的動作。
三:類加載的流程
1:整體的流程圖
2:各個階段的解析
(1):加載
a:加載的類的字節碼文件以及二進制文件的來源
通過一個類的完整路徑查找此類字節碼文件(class 文件即二進制文件)。將二進制文件的靜態存儲結構轉化為方法區的運行時數據結構,并利用二進制流文件創建一個Class對象,存儲在 Java 堆中用于對方法區的數據結構引用的入口;
class 文件的來源:有一點需要注意的是類加載機制不僅可以從文件系統讀取 class 文件,也可以通過網絡獲取,其他 jar 包或者其他程序生成,如 JSP 應用。
b:類加載器
-
類加載器:講到類加載不得不講到類加載的順序和類加載器。Java 中大概有四種類加載器,分別是:啟動類加載器(Bootstrap ClassLoader),擴展類加載器(Extension ClassLoader),系統類加載器(System ClassLoader),自定義類加載器(Custom ClassLoader),依次屬于繼承關系(注意這里的繼承不是 Java 類里面的 extends)
啟動類加載器(Bootstrap ClassLoader):主要負責加載存放在Java_Home/jre/lib下,或被-Xbootclasspath參數指定的路徑下的,并且能被虛擬機識別的類庫(如rt.jar,所有的java.*開頭的類均被Bootstrap ClassLoader加載),啟動類加載器是無法被Java程序直接引用的。 -
擴展類加載器(Extension ClassLoader):主要負責加載器由sun.misc.Launcher$ExtClassLoader實現,它負責加載Java_Home/jre/lib/ext目錄中,或者由java.ext.dirs系統變量指定的路徑中的所有類庫(如javax.*開頭的類),開發者可以直接使用擴展類加載器。
-
系統類加載器(System ClassLoader):主要負責加載器由sun.misc.Launcher$AppClassLoader來實現,它負責加載用戶類路徑(ClassPath)所指定的類,開發者可以直接使用該類加載器,如果應用程序中沒有自定義過自己的類加載器,一般情況下這個就是程序中默認的類加載器。
-
自定義類加載器(Custom ClassLoader:自己開發的類加載器
c:雙親委派
如果一個類加載器需要加載類,那么首先它會把這個類加載請求委派給父類加載器去完成,如果父類還有父類則接著委托,每一層都是如此。
一直遞歸到頂層,當父加載器無法完成這個請求時,子類才會嘗試去加載。
(2):驗證
驗證的過程只要是保證 class 文件的安全性和正確性,確保加載了該 class 文件不會導致 JVM 出現任何異常,不會危害JVM 的自身安全。驗證包括對文件格式的驗證,元數據和字節碼的驗證。
(3):準備
準備階段是為類變量進行內存分配和初始化零值的過程。注意這時候分配的是類變量的內存,這些內存會在方法區中分配。此時不會分配實例變量的內存,因為實例變量是在實例化對象時一起創建在Java 堆中的。而且此時類變量是賦值為零值,即 int 類型的初值為 0,引用類型初值為 null,而不是代碼中顯示賦值的數值。
(4):解析
將常量池的符號引用轉化成直接引用。符號引用可以理解為只是個替代的標簽,比如你此時要做一個計劃,暫時還沒有人選,你設定了個 A 去做這個事。然后等計劃真的要落地的時候肯定要找到確定的人選,到時候就是小明去做一件事。
解析就是把 A(符號引用) 替換成小明(直接引用)。符號引用就是一個字面量,沒有什么實質性的意義,只是一個代表。直接引用指的是一個真實引用,在內存中可以通過這個引用查找到目標。
(5):初始化
初始化的階段是類加載的最后一步,這個階段主要是執行 java 代碼,進行相關初始化的動作;這時候就執行一些靜態代碼塊,為靜態變量賦值,這里的賦值才是代碼里面的賦值,準備階段只是設置初始值占個坑。
創作挑戰賽新人創作獎勵來咯,堅持創作打卡瓜分現金大獎總結
以上是生活随笔為你收集整理的类加载机制(整个过程详解)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 很适合学生的Win10二合一平板win1
- 下一篇: 风口浪尖,联想删除向美军捐赠电脑的新闻,