常用Java虚拟机调试和配置参数

跟踪调试参数

-XX:PrintGC                  //最简单的GC日志
-XX:PrintGCDetails           //输出GC详细信息
-XX:+PrintHeapAtGC           //在每次GC前后打印详细信息,如同
                             //—XX:PrintGCDetails最后输出一样
-XX:+PrintGCTimeStamps       //额外输出GC时间:虚拟机启动后的时间偏移量
-XX:+PrintGCApplicationConcurrentTime //应用程序的执行时间
-XX:+PrintGCApplicationStoppedTime //应用程序由于GC的停顿时间
-XX:+PrintReferenceGC        //跟踪GC时引用信息
-Xloggc:log/gc.log           //将GC日志输出到当前目录log文件夹下
                             //的gc.log文件中
-verbose:class               //跟踪类的加载与卸载
-XX:TraceClassLoading        //跟踪类的加载
-XX:TraceClassUnloading      //跟踪类的卸载
-XX:+PrintVMOptions          //打印虚拟机接受的显式命令行参数
-XX:+PrintCommandLineFlags   //打印虚拟机接受的显式和隐式命令行参数
-XX:+PrintFlagsFinal         //打印虚拟机所有参数的值

堆参数设置

  • 最大堆和初始堆

通过下面示例分析堆参数设置:

public class SimpleArgs {
    public static void main(String[] args) {
        System.out.print("maxMemory=");
        System.out.println(Runtime.getRuntime().maxMemory()+" bytes");
        System.out.print("freeMemory=");
        System.out.println(Runtime.getRuntime().freeMemory()+" bytes");
        System.out.print("totalMemory=");
        System.out.println(Runtime.getRuntime().totalMemory()+" bytes");

        byte[] bytes=new byte[1024*1024];
        System.out.println("分配了1M空间给数组");

        System.out.print("maxMemory=");
        System.out.println(Runtime.getRuntime().maxMemory()+" bytes");
        System.out.print("freeMemory=");
        System.out.println(Runtime.getRuntime().freeMemory()+" bytes");
        System.out.print("totalMemory=");
        System.out.println(Runtime.getRuntime().totalMemory()+" bytes");

        bytes=new byte[1024*1024*4];
        System.out.println("分配了4M空间给数组");

        System.out.print("maxMemory=");
        System.out.println(Runtime.getRuntime().maxMemory()+" bytes");
        System.out.print("freeMemory=");
        System.out.println(Runtime.getRuntime().freeMemory()+" bytes");
        System.out.print("totalMemory=");
        System.out.println(Runtime.getRuntime().totalMemory()+" bytes");
    }
}

编译成.class文件后,在Windows下找到class文件目录,shift+右键->在此处打开命令窗口,然后执行下面指令:

java -Xmx20m -Xms5m -XX:+PrintCommandLineFlags -XX:+PrintGCDetails -XX:+UseSerialGC SimpleArgs
-XX:InitialHeapSize=5242880 -XX:MaxHeapSize=20971520 -XX:+PrintCommandLineFlags -XX:+PrintGCDetails -XX:+UseCompressedClassPointers -XX:+UseCompressedOops -XX:-UseLargePagesIndividualAllocation -XX:+UseSerialGC
maxMemory=20316160 bytes
freeMemory=5072200 bytes
totalMemory=6094848 bytes
[GC (Allocation Failure) [DefNew: 1032K->192K(1856K), 0.0021823 secs] 1032K->660K(5952K), 0.0040585 secs] [Times: user=0.00 sys=0.00, real=0.00 secs]
分配了1M空间给数组
maxMemory=20316160 bytes
freeMemory=4337784 bytes
totalMemory=6094848 bytes
[GC (Allocation Failure) [DefNew: 1247K->0K(1856K), 0.0020978 secs][Tenured: 1684K->1684K(4096K), 0.0021361 secs] 1715K->1684K(5952K), [Metaspace: 2698K->2698K(1056768K)], 0.0045926 secs] [Times: user=0.00 sys=0.00, real=0.00 secs]
分配了4M空间给数组
maxMemory=20316160 bytes
freeMemory=4405888 bytes
totalMemory=10358784 bytes
Heap
 def new generation   total 1920K, used 50K [0x00000000fec00000, 0x00000000fee10000, 0x00000000ff2a0000)
  eden space 1728K,   2% used [0x00000000fec00000, 0x00000000fec0caf8, 0x00000000fedb0000)
  from space 192K,   0% used [0x00000000fedb0000, 0x00000000fedb0000, 0x00000000fede0000)
  to   space 192K,   0% used [0x00000000fede0000, 0x00000000fede0000, 0x00000000fee10000)
 tenured generation   total 8196K, used 5780K [0x00000000ff2a0000, 0x00000000ffaa1000, 0x0000000100000000)
   the space 8196K,  70% used [0x00000000ff2a0000, 0x00000000ff845118, 0x00000000ff845200, 0x00000000ffaa1000)
 Metaspace       used 2705K, capacity 4486K, committed 4864K, reserved 1056768K
  class space    used 302K, capacity 386K, committed 512K, reserved 1048576K

设置最大内存为20MB,最小为5MB,从log中当前最大的内存由-XX:MaxHeapSize=20971520(=20*1024*1024)指定。
而打印的最大可用内存(maxMemory=20316160 bytes)要比20971520略小。这是由于新生代的复制算法导致的from/to空间大小的浪费。从信息中可以看到from大小为 0x00000000fede0000-0x00000000fedb0000=0x20000=131072 byes,但是20971520 -131072=20840448>20316160 ,这是由于虚拟机并没有直接使用from/to的大小,而是进一步做了对其操作。

  • 新生代设置
-Xmn              //设置新生代绝对大小 :eden+from+to
-XX:SurvivorRatio //设置eden区和from/to区的比例
-XX:NewRatio      //老年代/新生代

这里写图片描述
来自《实战Java虚拟机》

栈溢出处理

-XX:+HeapDumpOnOutOfMemoryError //设置在内存溢出时,导出整个堆信息
-XX:HeapDumpPath=d:/save.dump //设置导出堆信息的存放路径

非堆区参数配置

  • 方法区配置

在JDK1.6、JDK1.7

-XX:PermSize //设置永久区初始大小
-XX:MaxPermSize //设置最大永久区

在JDK1.8中永久区被移除,使用元数据区存放类的元数据

-XX:MaxMetaspaceSize //设置最大元数据区,,默认只受系统可用内存限制
  • 栈配置
-Xss //指定线程的栈大小
  • 直接内存设置
-XX:MaxDirectMemorySize  //最大直接内存,默认为最大堆空间,击-Xmx

直接内存的访问要快于堆内存,但是在申请内存空间时堆空间的速度远远高于直接内存。

  • 虚拟机工作模式
-server     //收集更多系统性能信息,对程序进行优化,启动较慢
-client     //Client启动速度较快

注意

  • 堆内存和方法区属于不同的内存空间
  • 常量池JDK1.6是放在方法区当中;在JDK1.7中的常量池移到了堆中;在JDK1.8中移除整个永久代,常量池又移到元数据区当中。
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值