亚洲免费在线-亚洲免费在线播放-亚洲免费在线观看-亚洲免费在线观看视频-亚洲免费在线看-亚洲免费在线视频

深入Java,初探JVM

系統(tǒng) 1803 0

轉(zhuǎn)載自 ---- http://lrysir.iteye.com/blog/1153226


????? 這不是一篇描述jvm是什么的文章,也不介紹jvm跨平臺(tái)的特性,也不是講述jvm安全特性的文章,更不是講解jvm指令操作,數(shù)據(jù)運(yùn)算的文章, 本文重點(diǎn)講述 類型的生命周期。
類型的生命周期涉及到: 類的裝載、jvm體系結(jié)構(gòu)、垃圾回收機(jī)制。
為什么要講jvm體系結(jié)構(gòu)?? 因?yàn)轭惖难b載和垃圾回收機(jī)制都和jvm體系結(jié)構(gòu)息息相關(guān)。
那么什么是jvm體系結(jié)構(gòu)呢?
深入Java,初探JVM
? 當(dāng)jvm運(yùn)行起來的時(shí)候,它會(huì)向系統(tǒng)申請(qǐng)一片內(nèi)存區(qū)(不同的jvm實(shí)現(xiàn)可能不同,有些可以使用虛擬內(nèi)存),將這塊內(nèi)存分出一部分存儲(chǔ)許多東西,例如:程序 創(chuàng)建的對(duì)象,傳遞給方法的參數(shù),返回值,局部變量等等,我們將這塊內(nèi)存稱之為“運(yùn)行時(shí)數(shù)據(jù)區(qū)”, 運(yùn)行時(shí)數(shù)據(jù)區(qū)可以劃分成方法區(qū)、堆、java棧、pc寄存器、本地方法棧。
看到上面這幅圖,和這些解說你可能大概的明白jvm 體系是個(gè)啥樣子,但是你或許還不了解運(yùn)行時(shí)數(shù)據(jù)區(qū)里面方法區(qū)等用來干嘛的。

  • 方法區(qū):當(dāng)虛擬機(jī)裝載一個(gè)class文件的時(shí)候,它會(huì)從這個(gè)class文件包含的二進(jìn)制數(shù)據(jù)中解析類型信息。然這些類型信息放到方法區(qū)中。因?yàn)榉?法區(qū)是被所有線程共享的,所以必須考慮數(shù)據(jù)的線程安全。假如兩個(gè)線程都在試圖找lava的類,在lava類還沒有被加載的情況下,只應(yīng)該有一個(gè)線程去加 載,而另一個(gè)線程等待。
  • Pc寄存器:每個(gè)新線程產(chǎn)生都將得到自己的pc寄存器以及一個(gè)java棧幀。
  • 堆:存放程序運(yùn)行時(shí)產(chǎn)生的所有對(duì)象。堆是一個(gè)線程共享的內(nèi)存區(qū),所以我們寫多線程程序的時(shí)候需要考慮并發(fā)。
  • Java棧:java棧由許多棧幀組成的,如圖,當(dāng)一個(gè)線程調(diào)用java方法時(shí),虛擬機(jī)壓入一個(gè)新的棧幀到j(luò)ava棧中,當(dāng)方法返回的時(shí)候,這個(gè)棧幀被從java棧彈出并被拋棄。


深入Java,初探JVM

那么現(xiàn)在你應(yīng)該可以想象到一些jvm是怎么工作的了,是不是應(yīng)該接著講具體工作原理了呢?。但是不急,先了解下類的裝載機(jī)制。
了解類的裝載機(jī)制之前先了解jvm里面的類裝載器:Bootstrap? Loader、ExtClassLoader 、AppClassLoader;
ExtClassLoader (負(fù)責(zé)裝載jre下面的rt.jar, charsets.jar)和AppClassLoader(負(fù)責(zé)轉(zhuǎn)載classpath下面的類包)是ClassLoader(抽象類)的子類;
Bootstrap Loader(負(fù)責(zé)裝載jre核心類庫)是根裝載器是c/c++寫的在java里面看不到它。
這三個(gè)類裝載器存在父子關(guān)系,? 根裝載器是 ExtClassLoader父裝載器,ExtClassLoader是AppClassLoader父裝載器;
Jvm中類的裝載也是安全機(jī)制沙箱模型的第一道門檻。 Java裝載類使用“雙親委派模式”—即全盤負(fù)責(zé)委托機(jī)制。
好現(xiàn)在讓我們了解裝載大概流程;
??? 當(dāng)裝載一個(gè)類的時(shí)候,若是由用戶指定一個(gè)類裝載器裝載的話,那么那個(gè)類裝載器會(huì)先委派給父類裝載器,一直委派到根裝載器,如果裝載的是一個(gè) java.lang.String,由于它是核心類庫的而且已經(jīng)被裝載過了,那么就會(huì)直接返回一個(gè)class對(duì)象,那么如果是一個(gè)根裝載器找不到的類呢? 接著就會(huì)交給子類(下一級(jí)父類)裝載器,如果還是沒有找到類文件,接著就會(huì)由之前用戶指定的那個(gè)類裝載器裝載。(這里沒有說明裝載超類的過程,請(qǐng)勿疏 忽)。
如果是有人惡意的寫了一個(gè)基礎(chǔ)類java.lang.String,那么會(huì)影響虛擬機(jī)嗎? 不會(huì)因?yàn)檫@個(gè)類最終會(huì)交由根裝載器裝載,而根裝載器只會(huì)去jre核心類庫加載,最終返回的class類型并不是 用戶寫的String,而且系統(tǒng)自帶的String,也就是說用戶寫String永遠(yuǎn)不會(huì)被加載。
了解了類裝載器是怎么工作了之后,我們也需要了解下class文件格式;
Java代碼 ? 收藏代碼
  1. The?ClassFile?Structure??
  2. ClassFile{??
  3. u4?magic;???? //魔數(shù) ??
  4. u2?minor_version;? //class?次版本號(hào) ??
  5. u2?major_version;? //class?主版本號(hào)? ??
  6. u2?constant_pool_count;?? //常量池計(jì)數(shù) ??
  7. cp_info?constant_pool[constant_pool_count- 1 ];?? //常量池 ??
  8. u2?access_flags;??? //修飾符 ??
  9. u2?this_class;??/常量池索引??
  10. u2?interfaces_count;????
  11. u2?interfaces[interfaces_count];??
  12. u2?fields_count;??
  13. field_info?fields[fields_count];??
  14. u2?methods_count;??
  15. method_info?methods[methods_count];??
  16. u2?attributes_count;??
  17. attribute_info?attributes[attrributes_count];??
  18. }??


我們需要了解的有很多,但是我們難以理解的就是 cp_info? constant_pool 常量池;
一個(gè)常量池里面有很多表

CONSTANT_Utf8 UTF-8編碼的Unicode字符串
CONSTANT_Integer ? int類型的字面值
CONSTANT_Float float類型的字面值
CONSTANT_Long ???????? long類型的字面值
CONSTANT_Double double類型的字面值
CONSTANT_Class 對(duì)一個(gè)類或接口的符號(hào)引用
CONSTANT_String String類型字面值的引用
CONSTANT_Fieldref 對(duì)一個(gè)字段的符號(hào)引用
CONSTANT_Methodref ? 對(duì)一個(gè)類中方法的符號(hào)引用
CONSTANT_InterfaceMethodref 對(duì)一個(gè)接口中方法的符號(hào)引用
CONSTANT_NameAndType ? 對(duì)一個(gè)字段或方法的部分符號(hào)引用

這些表結(jié)構(gòu)我也不解釋了
如果對(duì)class文件不夠了解也沒什么關(guān)系,知道個(gè)大概也行。那么我們了解了 jvm體系,類裝載器工作流程,那么我們細(xì)看下 類裝載器工作中 ,jvm運(yùn)行時(shí)數(shù)據(jù)區(qū)的變化,方法區(qū)里面的結(jié)構(gòu)等等。
在類裝載的過程中, 每一個(gè)類裝載器都會(huì)在方法區(qū)里面形成一張表,這張表記載著該裝載器和對(duì)應(yīng)的類的權(quán)限定名。沒這么一張表就形成了jvm內(nèi)部的命名空間。同時(shí)在方法區(qū)里面還該類的常量池等信息。
那么說到這些,其實(shí)這個(gè)過程還是很模糊,而且很多知識(shí)也落下了,那么我們現(xiàn)在看一個(gè)詳細(xì)一點(diǎn)的裝載過程。
當(dāng)裝載一個(gè)普通的類的時(shí)候,即調(diào)用類裝載器的loadClass方法, 如果希望裝載的類還沒有被裝載到命名空間,那么jvm會(huì)傳遞一個(gè)該類型的全限定名給類裝載器,也就是常量池CONSTANT_Class_info(該表 存儲(chǔ)著父類、類裝載器等信息)入口的裝載器,來試圖裝載被引用的類型,如果發(fā)起引用的類型是被jvm裝載器定義的,那么由jvm類裝載器裝載,否則由用戶 自定義裝載器裝載,那么一旦被引用的類型被裝載了,jvm仔細(xì)檢查它的二進(jìn)制數(shù)據(jù),如果類是是一個(gè)類,并且不是java.lang.Object。 jvm根據(jù)數(shù)據(jù)得到它的全限定名進(jìn)行裝載(遞歸的應(yīng)用了)這個(gè)過程還需要遞歸超接口。

裝載差不多講完了,一個(gè)完整的過程 是:? 裝載—連接---初始化
那么連接和初始化就一帶而過了, 重點(diǎn)放在垃圾回收。
連接的過程主要是驗(yàn)證(確認(rèn)類型符合java語言的語義,并且它不會(huì)危及虛擬機(jī)的完整性)、準(zhǔn)備(java 虛擬機(jī)為類變量分配內(nèi)存,設(shè)計(jì)默認(rèn)初始值)、解析(在類型的常量池中尋找類、接口、字段和方法的符合引用,把這些符號(hào)引用替換成直接引用的過程)。
初始化的時(shí)候,如果類存在直接超類,且超類還沒有被初始化,就先初始化直接超類。初始化接口并不需要初始化它的父接口。
補(bǔ)充:
Jvm當(dāng)運(yùn)行某個(gè)方法的時(shí)候,先把這個(gè)方法壓入java棧中,里面包含局部變量等信息,那么對(duì)象放入哪里呢? 壓入棧的是對(duì)象的引用, 即變量,? 所有的對(duì)象都存儲(chǔ)在堆中。
為什么要把對(duì)象放入堆,把變量之類的數(shù)據(jù)放入棧呢?? 說白了,對(duì)象太大了,存入棧中運(yùn)算麻煩。(當(dāng)然標(biāo)準(zhǔn)的回答不是這樣的,我這里僅僅是說明實(shí)質(zhì))

了解了這么一個(gè)過程之后,我們必然要了解垃圾回收機(jī)制了。
基本回收算法
1. 引用計(jì)數(shù):比較古老的回收算法。原理是此對(duì)象有一個(gè)引用,即增加一個(gè)計(jì)數(shù),刪除一個(gè)引用則減少一個(gè)計(jì)數(shù)。垃圾回收時(shí),只用收集計(jì)數(shù)為0的對(duì)象。此算法最致命的是無法處理循環(huán)引用的問題。
2. 標(biāo)記-清除:此算法執(zhí)行分兩階段。第一階段從引用根節(jié)點(diǎn)開始標(biāo)記所有被引用的對(duì)象,第二階段遍歷整個(gè)堆,把未標(biāo)記的對(duì)象清除。此算法需要暫停整個(gè)應(yīng)用,同時(shí),會(huì)產(chǎn)生內(nèi)存碎片。
3. 復(fù)制:此算法把內(nèi)存空間劃為兩個(gè)相等的區(qū)域,每次只使用其中一個(gè)區(qū)域。垃圾回收時(shí),遍歷當(dāng)前使用區(qū)域,把正在使用中的對(duì)象復(fù)制到另外一個(gè)區(qū)域中。次算法每 次只處理正在使用中的對(duì)象,因此復(fù)制成本比較小,同時(shí)復(fù)制過去以后還能進(jìn)行相應(yīng)的內(nèi)存整理,不過出現(xiàn)“碎片”問題。當(dāng)然,此算法的缺點(diǎn)也是很明顯的,就是 需要兩倍內(nèi)存空間。
4. 標(biāo)記-整理:此算法結(jié)合了“標(biāo)記-清除”和“復(fù)制”兩個(gè)算法的優(yōu)點(diǎn)。也是分兩階段,第一階段從根節(jié)點(diǎn)開始標(biāo)記所有被引用對(duì)象,第二階段遍歷整個(gè)堆,把清除 未標(biāo)記對(duì)象并且把存活對(duì)象“壓縮”到堆的其中一塊,按順序排放。此算法避免了“標(biāo)記-清除”的碎片問題,同時(shí)也避免了“復(fù)制”算法的空間問題。
5. 增量收集:實(shí)施垃圾回收算法,即:在應(yīng)用進(jìn)行的同時(shí)進(jìn)行垃圾回收。
6. 分代:基于對(duì)對(duì)象生命周期分析后得出的垃圾回收算法。把對(duì)象分為年青代、年老代、持久代,對(duì)不同生命周期的對(duì)象使用不同的算法(上述方式中的一個(gè))進(jìn)行回收。現(xiàn)在的垃圾回收器(從J2SE1.2開始)都是使用此算法的。

深入Java,初探JVM


更多文章、技術(shù)交流、商務(wù)合作、聯(lián)系博主

微信掃碼或搜索:z360901061

微信掃一掃加我為好友

QQ號(hào)聯(lián)系: 360901061

您的支持是博主寫作最大的動(dòng)力,如果您喜歡我的文章,感覺我的文章對(duì)您有幫助,請(qǐng)用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點(diǎn)擊下面給點(diǎn)支持吧,站長非常感激您!手機(jī)微信長按不能支付解決辦法:請(qǐng)將微信支付二維碼保存到相冊(cè),切換到微信,然后點(diǎn)擊微信右上角掃一掃功能,選擇支付二維碼完成支付。

【本文對(duì)您有幫助就好】

您的支持是博主寫作最大的動(dòng)力,如果您喜歡我的文章,感覺我的文章對(duì)您有幫助,請(qǐng)用微信掃描上面二維碼支持博主2元、5元、10元、自定義金額等您想捐的金額吧,站長會(huì)非常 感謝您的哦!!!

發(fā)表我的評(píng)論
最新評(píng)論 總共0條評(píng)論
主站蜘蛛池模板: 9l国产精品久久久久麻豆 | 亚洲h片| 国产亚洲福利精品一区 | 日本不卡专区 | 亚洲久草 | 日产国产欧美视频一区精品 | 色综合社区 | 国产一区二区不卡 | 精品96在线观看影院 | 久久美剧 | 毛片大全免费观看 | 欧美人猛交日本人xxx | 干干干操操操 | 欧美日本视频在线观看 | 色综合社区 | 国产在线精品成人一区二区三区 | 波多野结衣国产一区二区三区 | 毛片毛片毛片毛片出来毛片 | 激情综合婷婷 | 免费观看黄色a一级录像 | 四虎国产在线 | 国产美女白丝袜精品_a不卡 | 欧美日韩国产成人综合在线 | 亚洲成人伊人网 | 日韩三区 | 欧美日韩亚洲精品一区二区三区 | 在线欧美日韩国产 | 色综合久久综合网欧美综合网 | 国产高清美女一级a毛片久久w | 国产亚洲综合精品一区二区三区 | 奇米777777| 在线观看深夜视频 | 欧美成人全部免费观看1314色 | 国产区在线视频 | 爱爱爱免费视频 | 国内久久精品视频 | 欧美视频一区二区三区在线观看 | 91精品一区二区三区久久久久 | 日日添天天做天天爱 | 久久青草免费91线频观看站街 | 特级毛片在线播放 |