類裝載器就是錄找類的字節碼文件并構造出類的JVM內部表示對象的組件,在JAVA中,類裝載器把一個類裝入JVM中,
需要如下步驟:
1、裝載:查找和導入Class文件 2、鏈接:執行校驗,準備和解析步驟 1)、校驗:檢查載入Class文件數據的正確性 2)、準備:給類的靜態變量分配存儲空間。 3)、解析:將符號引用轉換成直接引用。 3、初始化:對類的靜態變量,靜態代碼塊執行初始化操作。
類裝載工作有ClassLoader及其子類負責,ClassLoader是一個運行時系統組件,它負責在運行時查找和裝入Class子節碼文件。
JVM在運行時會產生3個ClassLoader:
1、根裝載器
根裝載器不是ClassLoader的子類,它由C++語言編寫,所以在JAVA中找不到它,它主要負責裝載JRE的核心類庫,如JRE目標下的rt.jar、charsets.jar等
2、擴展類裝載器(ExtClassLoader)
ExtClassLoader負責裝載JRE擴展目錄ext中的JAR類包;
3、應用類裝載器(AppClassLoader)
AppClassLoader負責裝載Classpath路徑下的類包;
根裝載器,擴展類裝載器(ExtClassLoader),應用類裝載器(AppClassLoader)之間存在父子關系,其中ExtClassLoader和AppClassLoader都是ClassLoader的子類;
根裝載器是ExtClassLoader的父裝載器
ExtClassLoader是AppClassLoader的父裝載器;默認情況使用AppClassLoader裝載應用程序的類;
示例
public static void main(String[] args) { /*ApplicationContext ac=new ClassPathXmlApplicationContext("beans.xml"); HelloWorld helloWorld=(HelloWorld)ac.getBean("helloWorld"); helloWorld.say();*/ ClassLoader loader=Thread.currentThread().getContextClassLoader(); System.out.println(loader); System.out.println(loader.getParent()); System.out.println(loader.getParent().getParent()); }
輸出結果: sun.misc.Launcher$AppClassLoader@659e0bfd sun.misc.Launcher$ExtClassLoader@6d06d69c null
說明: 1、當前ClassLoader是AppClassLoader 2、父類ClassLoader是ExtClassLoader 3、父類的父類是根裝載器(JAVA中無法獲得它的句柄,所以僅返回null)
如何理解JVM裝載器的“全盤負責委托機制”?
“全盤負責”是指當一個ClassLoader裝載一個類時,除非顯式的使用另一個ClassLoader,該類所依賴及引用的類也由之個ClassLoader載入;
“委托機制”是指先委托父裝載器尋找目標類,只有在找不到的情況下才從自己的類路徑中查找并裝載目標類。