Java深刻 - Java內存區域詳解

Java和c c++不同,c c++都是直接經過手動的方式來申請內存,釋放內容。而java擁有良好的內存自動管理機制。因此在咱們開發java程序代碼的時候,通常狀況下不須要關心java的內存問題。java

Java的內存區域圖:c++

上面的圖就是Java運行時的內存數據區域。分紅方法區,虛擬機棧,本地方法棧,堆,程序計數器。數組

 

程序計數器

做用:程序計數器是一塊很小的內存空間,主要是線程所執行的字節碼的行號指示器。每一個線程都會有獨立的程序計數器。工具

 

虛擬機棧

Java的虛擬機棧也是線程私有的,生命週期和線程相同。虛擬機棧描述的是Java方法執行的內存模型:每一個方法被執行的時候都會同時建立一個棧幀(Stack Frame)用於存儲局部變量表、操做數棧、動態連接、方法出口等信息。每一個方法被調用直至執行完成的過程,就是對應着一個棧幀在VM Stack中從入棧到出棧的過程。spa

本地方法棧主要爲虛擬機使用的Native方法服務,也是棧的一部分。線程

虛擬機棧會拋兩種異常:code

1. StackOverflowError異常。一般主要是線程請求的棧深度大於虛擬機所容許的深度。好比遞歸層次太深就有可能致使這個異常出現,通常1000-2000層之間。減小遞歸層次能夠減少這個防範。也能夠經過參數-Xss128k 能夠設置每一個線程的棧大小。對象

2. OutOfMemoryError異常。主要是內存不夠。遞歸

 

Java堆

Java內存中最大的塊就是堆。全部的對象實例和數組都會分配在java的堆上面。Java堆也是內存GC的重要區域。生命週期

Java堆異常:

1. OutOfMemoryError異常。Java堆內存溢出能夠經過設置參數-Xmx3550m -Xms3550m來控制堆內存的大小。-Xms是最小值,-Xmx是最大值。

通常堆溢出:java.lang.OutOfMemoryError: Java heap space

異常提示中都有Java heap space 說明是堆溢出。

通常解決堆溢出思路有三種:

1. 經過內存影像分析工具(Eclipse Memory Analyzer)來定位堆溢出問題

2. 分析是否有內存泄露

3. 調整堆參數。

 

方法區

方法區也是各線程共享的內存區域,主要存放虛擬機加載的類信息、常量、靜態變量等信息。

運行時常量池也是方法區的一部分,做用是存儲編譯期生成的各類字面量和符號引用。

1. OutOfMemoryError異常。發生異常時,主要拋下面相似的異常信息:

 

Exception in thread "main" java.lang.OutOfMemoryError: PermGen space  
    at java.lang.String.intern(Native Method)  
    at org.fenixsoft.oom.RuntimeConstantPoolOOM.main(RuntimeConstantPoolOOM.java:18)


能夠看到有 PermGen space的提示則表示方法區溢出。

 

方法區溢出,能夠經過限制方法區的內存大小來限制:-XX:PermSize 和 -XX:MaxPermSize

Java1.7的PermGen默認空間爲85 MB(或者能夠經過-XX:MaxPermSize=XXXm指定)

須要注意的是,PermGen space是Oracle-Sun Hotspot纔有,JRockit以及J9是沒有這個區域。

相關文章
相關標籤/搜索