3、GC常用参数

1.堆分配参数

-Xms5m(初始化堆空间) -Xmx20m(最大堆空间) -XX:+PrintGCDetails(详细GC日志) -XX:+UseSerialGC(串行收集算法,Hotspot默认是并行的) -XX:+PrintCommandLineFlags (打印这些命令行)

 

package com.caolihua;


public class Test01 {

    public static void main(String[] args) {

        //-Xms5m -Xmx20m -XX:+PrintGCDetails -XX:+UseSerialGC -XX:+PrintCommandLineFlags
        
        //查看GC信息
        System.out.println("max memory:" + Runtime.getRuntime().maxMemory()/(1024*1024.0));
        System.out.println("free memory:" + Runtime.getRuntime().freeMemory()/(1024*1024.0));
        System.out.println("total memory:" + Runtime.getRuntime().totalMemory()/(1024*1024.0));
        
        byte[] b1 = new byte[1*1024*1024];
        System.out.println("分配了1M");
        System.out.println("max memory:" + Runtime.getRuntime().maxMemory()/(1024*1024.0));
        System.out.println("free memory:" + Runtime.getRuntime().freeMemory()/(1024*1024.0));
        System.out.println("total memory:" + Runtime.getRuntime().totalMemory()/(1024*1024.0));
        
        byte[] b2 = new byte[4*1024*1024];
        System.out.println("分配了4M");
        System.out.println("max memory:" + Runtime.getRuntime().maxMemory()/(1024*1024.0));
        System.out.println("free memory:" + Runtime.getRuntime().freeMemory()/(1024*1024.0));
        System.out.println("total memory:" + Runtime.getRuntime().totalMemory()/(1024*1024.0));
        
    }
    
}

 打印结果输出:

-XX:InitialHeapSize=5242880 -XX:MaxHeapSize=20971520 -XX:+PrintCommandLineFlags -XX:+PrintGCDetails -XX:+UseCompressedClassPointers -XX:+UseCompressedOops -XX:-UseLargePagesIndividualAllocation -XX:+UseSerialGC 
max memory:19.375
free memory:5.007911682128906
total memory:5.8125
[GC (Allocation Failure) [DefNew: 823K->191K(1856K), 0.0037429 secs] 823K->556K(5952K), 0.0038460 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] 
分配了1M
max memory:19.375
free memory:4.2360382080078125
total memory:5.8125
[GC (Allocation Failure) [DefNew: 1249K->0K(1856K), 0.0032904 secs][Tenured: 1581K->1581K(4096K), 0.0056323 secs] 1614K->1581K(5952K), [Metaspace: 2600K->2600K(1056768K)], 0.0090417 secs] [Times: user=0.02 sys=0.00, real=0.01 secs] 
分配了4M
max memory:19.375
free memory:4.301551818847656
total memory:9.87890625
Heap
 def new(1920K)=eden(1728K)+from/to(192K) def
new generation(不同收集算法,这里新生代写法不一样,默认是串行) total 1920K, used 69K [0x00000000fec00000, 0x00000000fee10000, 0x00000000ff2a0000) //这里计算结果要略微小于总的边界差值空间 eden space 1728K, 3% used [0x00000000fec00000, 0x00000000fec11440, 0x00000000fedb0000)//分别表示:上(a)、当前(b)、最大边界(c),1728K=转10进制(c-a)/1024 from space 192K, 0% used [0x00000000fedb0000, 0x00000000fedb0000, 0x00000000fede0000) to space 192K, 0% used [0x00000000fede0000, 0x00000000fede0000, 0x00000000fee10000) tenured generation total 8196K, used 5677K [0x00000000ff2a0000, 0x00000000ffaa1000, 0x0000000100000000) the space 8196K, 69% used [0x00000000ff2a0000, 0x00000000ff82b448, 0x00000000ff82b600, 0x00000000ffaa1000) Metaspace used 2607K, capacity 4486K, committed 4864K, reserved 1056768K class space used 278K, capacity 386K, committed 512K, reserved 1048576K

 

JVM内存分配情况:

max memory:19.375      JVM最大内存
free memory:4.973960876464844      total里面的,未被使用的内存
total memory:5.8125      JVM已经申请到的内存

也就是说:剩余的可用内存是max-total+free

 

2. 当前java项目根目录生成log日志文件

-Xloggc:log/gc.log

 

3.每发生一次GC,打印GC前后的堆内存变化;PrintGCDetails是程序结束后,打印最后一次

-XX:+PrintHeapAtGC

4.监控类加载

-XX:+TraceClassLoading

[Opened C:\Program Files\Java\jdk1.8.0_31\jre\lib\rt.jar]
[Loaded java.lang.Object from C:\Program Files\Java\jdk1.8.0_31\jre\lib\rt.jar]
[Loaded java.io.Serializable from C:\Program Files\Java\jdk1.8.0_31\jre\lib\rt.jar]
[Loaded java.lang.Comparable from C:\Program Files\Java\jdk1.8.0_31\jre\lib\rt.jar]
[Loaded java.lang.CharSequence from C:\Program Files\Java\jdk1.8.0_31\jre\lib\rt.jar]
[Loaded java.lang.String from C:\Program Files\Java\jdk1.8.0_31\jre\lib\rt.jar]

5.程序运行过程中,按下Ctrl+Break后,打印类的信息

-XX:+PrintClassHistogram

6.新生代(eden,from,to)+老年代=堆内存   //(from空间=to空间)

Xmn1m 设置新生代的空间,XX:SurvivorRatio,设置新生代伊甸园和from或to区间的比值,可观察以下结果。

-Xms20m -Xmx20m -Xmn1m -XX:SurvivorRatio=2 -XX:+PrintGCDetails -XX:+UseSerialGC

package com.caolihua;

public class Test02 {

    public static void main(String[] args) {
        
    
        byte[] b = null;
        //连续向系统申请空间,总共shenqing
        for(int i = 0 ; i <10; i ++){
            b = new byte[1*1024*1024];
        }
    }
}

 

打印结果:

Heap
def new generation total 768K, used 497K [0x00000000fec00000, 0x00000000fed00000, 0x00000000fed00000)
eden space 512K, 47% used [0x00000000fec00000, 0x00000000fec3c5e0, 0x00000000fec80000)
from space 256K, 99% used [0x00000000fecc0000, 0x00000000fecffff8, 0x00000000fed00000)
to space 256K, 0% used [0x00000000fec80000, 0x00000000fec80000, 0x00000000fecc0000)
tenured generation total 19456K, used 10409K [0x00000000fed00000, 0x0000000100000000, 0x0000000100000000)
the space 19456K, 53% used [0x00000000fed00000, 0x00000000ff72a440, 0x00000000ff72a600, 0x0000000100000000)
Metaspace used 2553K, capacity 4486K, committed 4864K, reserved 1056768K
class space used 273K, capacity 386K, committed 512K, reserved 1048576K

--------------------------------------------

XX:NewRatio:设置老年代和新生代空间比值

-Xms20m -Xmx20m -XX:NewRatio=2 -XX:+PrintGCDetails -XX:+UseSerialGC

Heap
def new generation total 6144K, used 1079K [0x00000000fec00000, 0x00000000ff2a0000, 0x00000000ff2a0000)
eden space 5504K, 19% used [0x00000000fec00000, 0x00000000fed0ddb0, 0x00000000ff160000)
from space 640K, 0% used [0x00000000ff160000, 0x00000000ff160000, 0x00000000ff200000)
to space 640K, 0% used [0x00000000ff200000, 0x00000000ff200000, 0x00000000ff2a0000)
tenured generation total 13696K, used 2564K [0x00000000ff2a0000, 0x0000000100000000, 0x0000000100000000)
the space 13696K, 18% used [0x00000000ff2a0000, 0x00000000ff521220, 0x00000000ff521400, 0x0000000100000000)
Metaspace used 2553K, capacity 4486K, committed 4864K, reserved 1056768K
class space used 273K, capacity 386K, committed 512K, reserved 1048576K

大伙可以算一下这个比例是否符合。

结论:新生代的大小一般设置是整个JVM堆空间的1/3~1/4左右,新生代过小,会引起频繁的GC,浪费性能;具体性能测试还是要根据你的程序,常驻内存的占多少?应该会有这种测试软件吧?

 7.堆内存溢出package com.calihua;

import java.util.Vector;

public class Test03 {

    public static void main(String[] args) {
        //设置为1M,会堆内存溢出,频繁gc但是还是会超过1m,设置为4M,虽然小于5M,但是频繁GC,使得最大超不过4M,所以不会溢出
//
//-XX:HeapDumpPath=d:/Test03.dump :生成报错文件,可以用工具去打开查看,但是有更方便的工具总体宏观把控,所以一般不这样搞。
//-Xms1m -Xmx1m -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=d:/Test03.dump -XX:+PrintGCDetails //堆内存溢出
    //共创建5M
Vector v = new Vector(); for(int i=0; i < 5; i ++){ v.add(new Byte[1*1024*1024]); } } }

8.栈空间设置:栈空间决定了一个线程栈的大小,即线程纵向调用最大深度。

package com.calihua;

public class Test04 {

    //-Xss1m  
    //-Xss5m
    
    //栈调用深度
    private static int count;
    
    public static void recursion(){
        count++;
        recursion();
    }
    public static void main(String[] args){
        try {
            recursion();
        } catch (Throwable t) {
            System.out.println("调用最大深入:" + count);
            t.printStackTrace();
        }
    }
}

报错:java.lang.StackOverflowError

9.方法区(永久区):亦所有线程共享区域,保存系统类信息,默认-XX:MaxPermSize=64M,也可以自定义设置,如果系统产生很多种类,需增大该空间

10.直接内存区:NIO的buffer区域,-XX:MaxDirectMemorySize 用Mycat、Socket通信时,要注意此类错误信息。

据说是比堆空间读写速度还要快?

 

 

posted on 2017-05-03 16:30  老曹123  阅读(385)  评论(0)    收藏  举报

导航