JVM 類加載

一、什么是類的加載

類的加載指的是將類的.class文件中的二進(jìn)制數(shù)據(jù)讀入到內(nèi)存中痹换,將其放在運(yùn)行時(shí)數(shù)據(jù)區(qū)的方法區(qū)內(nèi)征字,然后在堆區(qū)創(chuàng)建一個(gè)java.lang.Class對(duì)象,用來封裝類在方法區(qū)內(nèi)的數(shù)據(jù)結(jié)構(gòu)晴音。類的加載的最終產(chǎn)品是位于堆區(qū)中的Class對(duì)象柔纵,Class對(duì)象封裝了類在方法區(qū)內(nèi)的數(shù)據(jù)結(jié)構(gòu),并且向Java程序員提供了訪問方法區(qū)內(nèi)的數(shù)據(jù)結(jié)構(gòu)的接口锤躁。

  • 啟動(dòng)類加載器:Bootstrap ClassLoader,負(fù)責(zé)加載存放在JDK\jre\lib(JDK代表JDK的安裝目錄,下同)下系羞,或被-Xbootclasspath參數(shù)指定的路徑中的郭计,并且能被虛擬機(jī)識(shí)別的類庫
  • 擴(kuò)展類加載器:Extension ClassLoader,該加載器由sun.misc.Launcher$ExtClassLoader實(shí)現(xiàn)椒振,它負(fù)責(zé)加載DK\jre\lib\ext目錄中昭伸,或者由java.ext.dirs系統(tǒng)變量指定的路徑中的所有類庫(如javax.*開頭的類),開發(fā)者可以直接使用擴(kuò)展類加載器澎迎。
  • 應(yīng)用程序類加載器:Application ClassLoader庐杨,該類加載器由sun.misc.Launcher$AppClassLoader來實(shí)現(xiàn),它負(fù)責(zé)加載用戶類路徑(ClassPath)所指定的類夹供,開發(fā)者可以直接使用該類加載器

二灵份、

三、JVM加載class文件的原理

JVM中類的裝載是由類加載器(ClassLoader)和它的子類來實(shí)現(xiàn)的哮洽,Java中的類加載器是一個(gè)重要的Java運(yùn)行時(shí)系統(tǒng)組件填渠,它負(fù)責(zé)在運(yùn)行時(shí)查找和裝入類文件中的類。

由于Java的跨平臺(tái)性鸟辅,經(jīng)過編譯的Java源程序并不是一個(gè)可執(zhí)行程序氛什,而是一個(gè)或多個(gè)類文件。當(dāng)Java程序需要使用某個(gè)類時(shí)匪凉,JVM會(huì)確保這個(gè)類已經(jīng)被加載枪眉、連接(驗(yàn)證、準(zhǔn)備和解析)和初始化再层。類的加載是指把類的.class文件中的數(shù)據(jù)讀入到內(nèi)存中瑰谜,通常是創(chuàng)建一個(gè)字節(jié)數(shù)組讀入.class文件,然后產(chǎn)生與所加載類對(duì)應(yīng)的Class對(duì)象树绩。加載完成后萨脑,Class對(duì)象還不完整,所以此時(shí)的類還不可用饺饭。當(dāng)類被加載后就進(jìn)入連接階段渤早,這一階段包括驗(yàn)證、準(zhǔn)備(為靜態(tài)變量分配內(nèi)存并設(shè)置默認(rèn)的初始值)和解析(將符號(hào)引用替換為直接引用)三個(gè)步驟瘫俊。最后JVM對(duì)類進(jìn)行初始化鹊杖,包括:

如果類存在直接的父類并且這個(gè)類還沒有被初始化,那么就先初始化父類扛芽;
如果類中存在初始化語句骂蓖,就依次執(zhí)行這些初始化語句。
  類的加載是由類加載器完成的川尖,類加載器包括:根加載器(BootStrap)登下、擴(kuò)展加載器(Extension)、系統(tǒng)加載器(System)和用戶自定義類加載器(java.lang.ClassLoader的子類)。

從Java 2(JDK 1.2)開始被芳,類加載過程采取了父親委托機(jī)制(PDM)缰贝。PDM更好的保證了Java平臺(tái)的安全性,在該機(jī)制中畔濒,JVM自帶的Bootstrap是根加載器剩晴,其他的加載器都有且僅有一個(gè)父類加載器。類的加載首先請(qǐng)求父類加載器加載侵状,父類加載器無能為力時(shí)才由其子類加載器自行加載赞弥。JVM不會(huì)向Java程序提供對(duì)Bootstrap的引用。下面是關(guān)于幾個(gè)類加載器的說明:

Bootstrap:一般用本地代碼實(shí)現(xiàn)趣兄,負(fù)責(zé)加載JVM基礎(chǔ)核心類庫(rt.jar)绽左;
Extension:從java.ext.dirs系統(tǒng)屬性所指定的目錄中加載類庫,它的父加載器是Bootstrap诽俯;
System:又叫應(yīng)用類加載器妇菱,其父類是Extension。它是應(yīng)用最廣泛的類加載器暴区。它從環(huán)境變量classpath或者系統(tǒng)屬性java.class.path所指定的目錄中記載類闯团,是用戶自定義加載器的默認(rèn)父加載器。

四仙粱、Java對(duì)象創(chuàng)建過程

(1)JVM遇到一條新建對(duì)象的指令時(shí)首先去檢查這個(gè)指令的參數(shù)是否能在常量池中定義到一個(gè)類的符號(hào)引用房交。然后加載這個(gè)類(類加載過程在后邊講)
(2)為對(duì)象分配內(nèi)存。一種辦法“指針碰撞”伐割、一種辦法“空閑列表”候味,最終常用的辦法“本地線程緩沖分配(TLAB)”
(3)將除對(duì)象頭外的對(duì)象內(nèi)存空間初始化為0
(4)對(duì)對(duì)象頭進(jìn)行必要設(shè)置

五、類的生命周期

類的生命周期包括這幾個(gè)部分隔心,加載白群、連接、初始化硬霍、使用和卸載帜慢,其中前三部是類的加載的過程,如下圖:

加載,查找并加載類的二進(jìn)制數(shù)據(jù)唯卖,在Java堆中也創(chuàng)建一個(gè)java.lang.Class類的對(duì)象
連接粱玲,連接又包含三塊內(nèi)容:驗(yàn)證、準(zhǔn)備拜轨、初始化抽减。
(1)驗(yàn)證,文件格式橄碾、元數(shù)據(jù)卵沉、字節(jié)碼颠锉、符號(hào)引用驗(yàn)證;
(2)準(zhǔn)備偎箫,為類的靜態(tài)變量分配內(nèi)存木柬,并將其初始化為默認(rèn)值皆串;
(3)解析淹办,把類中的符號(hào)引用轉(zhuǎn)換為直接引用
初始化,為類的靜態(tài)變量賦予正確的初始值
使用恶复,new出對(duì)象程序中使用
卸載怜森,執(zhí)行垃圾回收

六、Java對(duì)象結(jié)構(gòu)

Java對(duì)象由三個(gè)部分組成:

對(duì)象頭:由兩部分組成谤牡,第一部分存儲(chǔ)對(duì)象自身的運(yùn)行時(shí)數(shù)據(jù)副硅,第二部分是指針類型,指向?qū)ο蟮念愒獢?shù)據(jù)類型(即對(duì)象代表哪個(gè)類)翅萤。
自身的運(yùn)行時(shí)數(shù)據(jù):哈希碼恐疲、GC分代年齡、鎖標(biāo)識(shí)狀態(tài)套么、線程持有的鎖培己、偏向線程ID(一般占32/64 bit)。
PS:如果是數(shù)組對(duì)象胚泌,則對(duì)象頭中還有一部分用來記錄數(shù)組長(zhǎng)度省咨。
實(shí)例數(shù)據(jù):用來存儲(chǔ)對(duì)象真正的有效信息(包括父類繼承下來的和自己定義的)
對(duì)齊填充:JVM要求對(duì)象起始地址必須是8字節(jié)的整數(shù)倍(8字節(jié)對(duì)齊)

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市玷室,隨后出現(xiàn)的幾起案子零蓉,更是在濱河造成了極大的恐慌,老刑警劉巖穷缤,帶你破解...
    沈念sama閱讀 221,635評(píng)論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件敌蜂,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡津肛,警方通過查閱死者的電腦和手機(jī)章喉,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,543評(píng)論 3 399
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來快耿,“玉大人囊陡,你說我怎么就攤上這事∠坪ィ” “怎么了撞反?”我有些...
    開封第一講書人閱讀 168,083評(píng)論 0 360
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)搪花。 經(jīng)常有香客問我遏片,道長(zhǎng)嘹害,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 59,640評(píng)論 1 296
  • 正文 為了忘掉前任吮便,我火速辦了婚禮笔呀,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘髓需。我一直安慰自己许师,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,640評(píng)論 6 397
  • 文/花漫 我一把揭開白布僚匆。 她就那樣靜靜地躺著微渠,像睡著了一般。 火紅的嫁衣襯著肌膚如雪咧擂。 梳的紋絲不亂的頭發(fā)上逞盆,一...
    開封第一講書人閱讀 52,262評(píng)論 1 308
  • 那天,我揣著相機(jī)與錄音松申,去河邊找鬼云芦。 笑死,一個(gè)胖子當(dāng)著我的面吹牛贸桶,可吹牛的內(nèi)容都是我干的舅逸。 我是一名探鬼主播,決...
    沈念sama閱讀 40,833評(píng)論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼刨啸,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼堡赔!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起设联,我...
    開封第一講書人閱讀 39,736評(píng)論 0 276
  • 序言:老撾萬榮一對(duì)情侶失蹤善已,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后离例,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體换团,經(jīng)...
    沈念sama閱讀 46,280評(píng)論 1 319
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,369評(píng)論 3 340
  • 正文 我和宋清朗相戀三年宫蛆,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了艘包。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,503評(píng)論 1 352
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡耀盗,死狀恐怖想虎,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情叛拷,我是刑警寧澤舌厨,帶...
    沈念sama閱讀 36,185評(píng)論 5 350
  • 正文 年R本政府宣布,位于F島的核電站忿薇,受9級(jí)特大地震影響裙椭,放射性物質(zhì)發(fā)生泄漏躏哩。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,870評(píng)論 3 333
  • 文/蒙蒙 一揉燃、第九天 我趴在偏房一處隱蔽的房頂上張望扫尺。 院中可真熱鬧,春花似錦炊汤、人聲如沸正驻。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,340評(píng)論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽拨拓。三九已至肴颊,卻和暖如春氓栈,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背婿着。 一陣腳步聲響...
    開封第一講書人閱讀 33,460評(píng)論 1 272
  • 我被黑心中介騙來泰國打工授瘦, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人竟宋。 一個(gè)月前我還...
    沈念sama閱讀 48,909評(píng)論 3 376
  • 正文 我出身青樓提完,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國和親丘侠。 傳聞我的和親對(duì)象是個(gè)殘疾皇子徒欣,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,512評(píng)論 2 359

推薦閱讀更多精彩內(nèi)容