《深入理解java虛擬機》一書中介紹到jvm的內存溢出情況,對理解jvm的自動內存管理機制有一定幫助,下面通過幾個實例來進行說明。
java虛擬機的規范描述中,除了程序計數器外,java堆,虛擬機棧,本地方法區等運行時區都會發生outOfMemoryError的可能。
《1》java堆溢出
//eclipse-run configurations-VM arguments-Xms20M -Xmx20M -Xmn10M -XX:+HeapDumpOnOutOfMemoryError

public class HeapOOM{ static class OOMObject { } public static void main(String[] args) { List<OOMObject> list=new ArrayList<OOMObject>(); while(true) { list.add(new OOMObject()); } }}View Code《2》虛擬機棧和本地方法棧溢出
//-Xss128k
代碼一產生的是stackoverflowerror,

public class JVMStacks{ PRivate int stackLength=1; public void stackLeak() { stackLength++; stackLeak(); } public static void main(String[] args) { JVMStacks oom=new JVMStacks(); try { oom.stackLeak(); }catch(Throwable e) { System.out.println(oom.stackLength); throw new RuntimeException(e); } }}View Code//-Xss2M
通過代碼二可以產生內存溢出異常,但是往往會使你的計算機進入假死狀態

public void JAVAStack{ private void dostop(){ while(true){};}public void stackLeak(){ while(true){ Thread thread =new Thread(new Runnable(){ public void run(){dostop();}});thread.start();}}public void main(String[] args){JAVAStack oom=new JavaStack();oom.stackLeak();}}View Code《3》運行時常量池內存溢出
//-XX:PermSize=10M -XX:MaxPermSize=10M

public class RuntimeConstantPool{ /** * @param args */ public static void main(String[] args) { List<String> list=new ArrayList<String>(); int i=0; while(true) { list.add(String.valueOf(i++).intern()); } }}View Code《4》本機直接內存溢出

/** * VM Args:-Xmx20M -XX:MaxDirectMemorySize=10M * @author zzm */public class DirectMemoryOOM { private static final int _1MB = 1024 * 1024; public static void main(String[] args) throws Exception { Field unsafeField = Unsafe.class.getDeclaredFields()[0]; unsafeField.setaccessible(true); Unsafe unsafe = (Unsafe) unsafeField.get(null); while (true) { unsafe.allocateMemory(_1MB); } }}View Code新聞熱點
疑難解答