運行時數據區
?
java 虛擬機定義了若干種程序運行時使用到的運行時數據區
1.有一些是 ? 隨虛擬機的啟動而創建,隨虛擬機的退出而銷毀
2.第二種則是與線程一一對應,隨線程的開始和結束而創建和銷毀。
java 虛擬機所管理的內存將會包括以下幾個運行時數據區域
PC 寄存器
也叫程序計數器( Program Counter Register )是一塊較小的內存空間,它的作用可以看做是當前線程所執行的字節碼的信號指示器。
每一條 JVM 線程都有自己的 PC 寄存器
在任意時刻,一條 JVM 線程只會執行一個方法的代碼。該方法稱為該線程的當前方法( Current Method )
如果該方法是 java 方法,那 PC 寄存器保存 JVM 正在執行的字節碼指令的地址
如果該方法是 native ,那 PC 寄存器的值是 undefined 。
此內存區域是唯一一個在 Java 虛擬機規范中沒有規定任何 OutOfMemoryError 情況的區域。
?
Java 虛擬機棧
與 PC 寄存器一樣, java 虛擬機棧 ( Java Virtual Machine Stack )也是線程私有的。每一個 JVM 線程都有自己的 java 虛擬機棧,這個棧與線程同時創建,它的生命周期與線程相同。
虛擬機棧描述的是 Java 方法執行的內存模型:每個方法被執行的時候都會同時創建一個棧幀( Stack Frame )用于存儲局部變量表、操作數棧、動態鏈接、方法出口等信息。每一個方法被調用直至執行完成的過程就對應著一個棧幀在虛擬機棧中從入棧到出棧的過程。
JVM stack 可以被實現成固定大小,也可以根據計算動態擴展。
如果采用固定大小的 JVM stack 設計,那么每一條線程的 JVM Stack 容量應該在線程創建時獨立地選定。 JVM 實現應該提供調節 JVM Stack 初始容量的手段。
如果采用動態擴展和收縮的 JVM Stack 方式,應該提供調節最大、最小容量的手段。
?
JVM Stack 異常情況:
StackOverflowError :當線程請求分配的棧容量超過 JVM 允許的最大容量時拋出
OutOfMemoryError :如果 JVM Stack 可以動態擴展,但是在嘗試擴展時無法申請到足夠的內存去完成擴展,或者在建立新的線程時沒有足夠的內存去創建對應的虛擬機棧時拋出。
?
Java 堆
在 JVM 中,堆( heap )是可供各條 線程共享 的運行時內存區域,也是供所有類實例和數據對象分配內存的區域。
Java 堆載虛擬機啟動的時候就被創建,堆中儲存了各種對象,這些對象被自動管理內存系統( Automatic Storage Management System ,也即是常說的 “Garbage Collector (垃圾回收器) ” )所管理。這些對象無需、也無法顯示地被銷毀。
Java 堆的容量可以是固定大小,也可以隨著需求動態擴展,并在不需要過多空間時自動收縮。
Java 堆所使用的內存不需要保證是物理連續的,只要邏輯上是連續的即可。
JVM 實現應當提供給程序員調節 Java 堆初始容量的手段,對于可動態擴展和收縮的堆來說,則應當提供調節其最大和最小容量的手段。
Java 堆異常:
OutOfMemoryError :如果實際所需的堆超過了自動內存管理系統能提供的最大容量時拋出。
?
方法區( Method Area )
方法區是可供各條線程共享的運行時內存區域。存儲了每一個類的結構信息,例如運行時常量池( Runtime Constant Pool )、字段和方法數據、構造函數和普通方法的字節碼內容、還包括一些在類、實例、接口初始化時用到的特殊方法
方法區在虛擬機啟動的時候創建。
方法區的容量可以是固定大小的,也可以隨著程序執行的需求動態擴展,并在不需要過多空間時自動收縮。
方法區在實際內存空間中可以是不連續的。
Java 虛擬機實現應當提供給程序員或者最終用戶調節方法區初始容量的手段,對于可以動態擴展和收縮方法區來說,則應當提供調節其最大、最小容量的手段。
Java 方法區異常:
OutOfMemoryError : ? 如果方法區的內存空間不能滿足內存分配請求,那 Java 虛擬機將拋出一個 OutOfMemoryError 異常。
?
運行時常量池( Runtime Constant Pool )
運行時常量池是每一個類或接口的常量池( Constant_Pool )的運行時表現形式,它包括了若干種常量:編譯器可知的數值字面量到必須運行期解析后才能獲得的方法或字段的引用。
運行時常量池是方法區的一部分。 每一個運行時常量池都分配在 JVM 的方法區中,在類和接口被加載到 JVM 后,對應的運行時常量池就被創建。
在創建類和接口的運行時常量池時,可能會遇到的異常:
OutOfMemoryError :當創建類和接口時,如果構造運行時常量池所需的內存空間超過了方法區所能提供的最大內存空間后就會拋出 OutOfMemoryError
?
本地方法棧
Java 虛擬機可能會使用到傳統的棧來支持 native 方法(使用 Java 語言以外的其它語言編寫的方法)的執行,這個棧就是本地方法棧( Native Method Stack )
如果 JVM 不支持 native 方法,也不依賴與傳統方法棧的話,可以無需支持本地方法棧。
如果支持本地方法棧,則這個棧一般會在線程創建的時候按線程分配。
異常情況:
StackOverflowError :如果線程請求分配的棧容量超過本地方法棧允許的最大容量時拋出
OutOfMemoryError :如果本地方法棧可以動態擴展,并且擴展的動作已經嘗試過,但是目前無法申請到足夠的內存去完成擴展,或者在建立新的線程時沒有足夠的內存去創建對應的本地方法棧,那 Java 虛擬機將會拋出一個 OutOfMemoryError 異常。 ?
更多文章、技術交流、商務合作、聯系博主
微信掃碼或搜索:z360901061

微信掃一掃加我為好友
QQ號聯系: 360901061
您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。
【本文對您有幫助就好】元
