jvm - jvm堆参数调优 & OutOfMemoryError的dmeo

堆参数的调优(我们说JVM调优,其本质就是对参数的调优)

在jdk1.7下(已过时):

其中:
1)-Xms:start(默认为1/64,)
2)-Xmx:max (默认为1/4,即默认堆的最大值是物理内存的1/4)
堆的初始大小和最大值,两者最好一致,避免内存大小调整影响运行的性能

3)-Xmn:new
之前学过堆物理上,新生代和老年代的比例为1:2

所以想要修改这个比例,就是调整 -Xmn 的大小,
但是这个参数,一般不调。

下面两个参数一辈子用不上,因为jdk1.8取消了永久代,变成了元空间。
4)-XX:PermSize:永久代的初始大小
5)-XX:MaxPermSize:永久代的最大值

在jdk1.8下:

 

1.如何证明jdk1.8的堆内存由新生区+养老区+元空间?
使用-XX:+PrintGCDetails来证明(在IDEA中配置)(它可以输出详细的GC处理日志)

2.如何造成OOM?(堆内存干爆)(当养老代都满了的时候,就会OOM)
(为了快速干爆,记得在IDEA里面修改一下它的-Xms10m -Xmx10m,改为10M)

nextInt(n)  随机生成一个范围在[0 ,n)之间的整型
上面这个例子会OOM的原因是字符串常量池从jdk1.7开始移到了堆里(其实1.8也会,因为毕竟你也在不停地new对象到堆中)

结果:(先GC,后Full GC,如果Full GC都不能清理出空间了,则最后报错)

原因:

3.物理内存16G,JVM的堆内存可以分到多少?
初始分配大小(-Xms)为1/64(约200多MB),随着使用,最大(-Xmx)可为1/4(约3.6GB)
通过代码验证:
每一个JavaAPP对应一个runtime对象(见本文JVM图的绿色方框部分)(Runtime Data Area),里面封装了这个app里面的各种信息。

long a = Runtime.getRuntime().totalMemory();
long b = Runtime.getRuntime().maxMemory();
System.out.println(a/(double)1024/1024);
System.out.println(b/(double)1024/1024);

结果:

实际生产,要设-Xms和-Xmx一样大,防止内存忽高忽低,避免在GC后调整堆大小带来的压力。
在IDEA中怎么设置:

配置之后,运行结果:
(可以看到,堆的初始=最大上限,还可以看到详细日志,里面有初生代、老年代、元空间)


运行结果里面,通过计算还可以证明物理上,堆内存物理上只分为新生代+养老代:
(图中的篮框里应改为“元空间”,这里写错了)

永久代和元空间最大的区别:
永久代使用的内存是Java虚拟机的堆内存;
元空间使用的内存是本机的物理内存。(所以,默认情况下元空间的大小仅受本地内存的限制)

 

后面针对-XX:+PrintGCDetails的输出结果,进行了详细讲解,说明了这些输出的具体含义,而不仅仅停留在GC、Full GC了
GC:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值