jvm結(jié)構(gòu):
1.程序計(jì)數(shù)器,每個(gè)線程都有自己的計(jì)數(shù)器,用于記錄字節(jié)碼指令的執(zhí)行位置
2.虛擬機(jī)棧,用于存放棧幀,棧幀中包含,局部變量表 渺绒、操作數(shù)棧部脚、動(dòng)態(tài)鏈接姻采、方法出口.每個(gè)線程都有自己的虛擬機(jī)棧.調(diào)用執(zhí)行任何方法的時(shí)候做祝,都會(huì)給方法創(chuàng)建棧幀近尚,然后入棧
3.堆內(nèi)存,對(duì)象信息存放其中,棧幀中的局部變量指向堆內(nèi)存中的對(duì)象
4.方法區(qū) / Metaspace,主要還是存放我們自己寫的各種類相關(guān)的信息
5.本地方法棧,存儲(chǔ)結(jié)構(gòu)與虛擬機(jī)棧類似,用于jdk底層相關(guān)的局部變量之類的信息
6.堆外內(nèi)存,不屬于JVM的,可以在Java堆外分配內(nèi)存空間蠕啄。通過虛擬機(jī)的DirectByteBuffer來(lái)引用.可以提升性能
總結(jié)
最后做一點(diǎn)總結(jié),我們的Java代碼通過JVM來(lái)運(yùn)行時(shí):
首先一定會(huì)一行一行執(zhí)行編譯好的字節(jié)碼指令戈锻。
然后在執(zhí)行的過程中歼跟,對(duì)于方法的調(diào)用,會(huì)通過Java虛擬機(jī)棧來(lái)為每個(gè)方法創(chuàng)建棧幀來(lái)入棧和出棧格遭,而且棧幀里有方法的局部變量表哈街。
接著對(duì)于對(duì)象的創(chuàng)建,會(huì)分配到Java堆內(nèi)存里去
對(duì)于類信息的存儲(chǔ)拒迅,會(huì)放在方法區(qū) / Metaspace這樣的區(qū)域里骚秦。
另外有兩塊特殊的區(qū)域:
本地方法棧,是執(zhí)行native方法時(shí)候用的棧璧微,跟Java虛擬機(jī)棧是類似的
堆外內(nèi)存作箍,可以在Java堆外分配內(nèi)存空間來(lái)存儲(chǔ)一些對(duì)象
OOM的四種情況
1.Java堆溢出:heap
java.lang.OutofMemoryError:Java?heap space
2.棧溢出:stack
java.lang.StackOverflowError
3.運(yùn)行時(shí)常量溢出 ? constant
java.lang.OutofMemoryError: PermGen space
4.方法區(qū)溢出 ? directMemory
java.lang.OutofMemoryError: PermGen space