JVM设置Young Gen的大小疑问
设置年轻代的3组参数有优先级区别
设置Young Generation的大小(假设设为1024m),似乎有很多参数,大概分为3组:
(1)-XX:NewSize=1024m和-XX:MaxNewSize=1024m;
(2)-Xmn1024m;
(3)-XX:NewRatio=2; (假设Heap总共是3G)
很奇怪,为什么hotspot的JVM设置Young Gen会冒出这么多组参数呢?难道是历史原因么?如果这样的话,我们3组混合着用,谁覆盖谁呢???
笔者找了些资料,也做了些实验,得出一下结论:
(1)最高优先级: -XX:NewSize=1024m和-XX:MaxNewSize=1024m
(2)次高优先级: -Xmn1024m (默认等效效果是:-XX:NewSize==-XX:MaxNewSize==1024m)
(3)最低优先级:-XX:NewRatio=2
推荐使用的是-Xmn参数,原因是这个参数很简洁,相当于一次性设定NewSize和MaxNewSIze,而且两者相等。-Xmn配合-Xms堆起始大小和-Xmx堆最大大小,恰好把堆内存布局确定完了(估计设计者也是因为简洁的原因,弄出了三个简写参数)。另外,官文似乎说-Xmn是1.4才开始支持的,但是如今应该没有还在用1.4之前的JRE的吧。
官文佐证
摘要1: 1.4之后,-Xmn以一抵二(-XX:NewSize和-XX:MaxNewSize)
http://www.oracle.com/technetwork/java/hotspotfaq-138619.html#gc_pause
you can adjust the size of the eden (young generation space) with -XX:NewSize=... and -XX:MaxNewSize=... (for 1.3/1.4) or -Xmn in 1.4 and later.
在1.3/1.4版本下,通过-XX:NewSize和-XX:MaxNewSize两个参数共同设置Young Gen的大小(原文笼统地把Young Gen当做Eden了)。
然后在1.4之后的版本,可以直接通过-Xmn来设置Young Gen的大小了。
笔者感觉:1.4后,设置Young Gen更方便了。
摘要2:1.4之后,还可以用-XX:NewRatio,-XX:MaxNewSize覆盖-XX:NewRatio
If you currently invoke with something like:
-Xms384m -Xmx384m -XX:NewSize=128m -XX:MaxNewSize=128m
which will dedicate 1/3rd of the memory to eden.
For 1.3, MaxNewSize is set to 32mb on Sparc, 2.5mb on Intel based machines. NewRatio (the ratio between the young/old generations) has values of 2 on Sparc Server, 12 on client Intel, and 8 everywhere else, as you can quickly determine, this is superseded by MaxNewSize's defaults (rendering NewRatio ineffective for even moderately sized heaps). I
In 1.4 and later, MaxNewSize has been effectively set to infinity, and NewRatio can be used instead to set the value of the new generation. Using the above as an example, you can do the following in 1.4 and later:
-Xms384m -Xmx384m -XX:NewRatio=2
笔者感觉:设置Young Gen有多个参数,大概跟历史版本原因有关系。不用去了解这些,需要了解的是这些参数一起用的时候,怎么办???做实验瞅瞅!!!
实验佐证
实验代码
public class JVMNewSize {
public static void main(String[] args) {
while(true) {
System.out.println("running ...");
try {
Thread.sleep(1000L*30);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
实验1:-Xmn以一抵二
[@zw_83_83 test]# java -Xms900m -Xmx900m -Xmn600m JVMNewSize
running ...
固定堆内存为900m,-Xmn指定Young Gen为600m。
[@zw_83_83 ~]# jps -m
5705 Jps -m
5681 JVMNewSize
[@zw_83_83 ~]# jmap -heap 5681
Attaching to process ID 5681, please wait...
Debugger attached successfully.
Server compiler detected.
JVM version is 20.1-b02
using thread-local object allocation.
Parallel GC with 13 thread(s)
Heap Configuration:
MinHeapFreeRatio = 40
MaxHeapFreeRatio = 70
MaxHeapSize = 943718400 (900.0MB) 最大堆内存是900m
NewSize = 629145600 (600.0MB)
MaxNewSize = 629145600 (600.0MB) Young 的确是600m
OldSize = 5439488 (5.1875MB)
NewRatio = 2
SurvivorRatio = 8
PermSize = 21757952 (20.75MB)
MaxPermSize = 85983232 (82.0MB)
Heap Usage:
PS Young Generation 年轻代:Eden+From+To 总共恰好是600m
Eden Space:
capacity = 471859200 (450.0MB)
used = 9437200 (9.000015258789062MB)
free = 462422000 (440.99998474121094MB)
2.000003390842014% used
From Space:
capacity = 78643200 (75.0MB)
used = 0 (0.0MB)
free = 78643200 (75.0MB)
0.0% used
To Space:
capacity = 78643200 (75.0MB)
used = 0 (0.0MB)
free = 78643200 (75.0MB)
0.0% used
PS Old Generation 年轻代占用了600m,自然老年代就300m
capacity = 314572800 (300.0MB)
used = 0 (0.0MB)
free = 314572800 (300.0MB)
0.0% used
PS Perm Generation
capacity = 21757952 (20.75MB)
used = 2606792 (2.4860305786132812MB)
free = 19151160 (18.26396942138672MB)
11.980870258377259% used
如果调整为-Xmn400呢?
[@zw_83_83 test]# java -Xms900m -Xmx900m -Xmn400m JVMNewSize
Heap Configuration:
MinHeapFreeRatio = 40
MaxHeapFreeRatio = 70
MaxHeapSize = 943718400 (900.0MB)
NewSize = 419430400 (400.0MB)
MaxNewSize = 419430400 (400.0MB)
OldSize = 5439488 (5.1875MB)
NewRatio = 2
SurvivorRatio = 8
PermSize = 21757952 (20.75MB)
MaxPermSize = 85983232 (82.0MB)
实验2:-Xmn被-XX:NewSize和-XX:MaxNewSize覆盖
1、 只覆盖NewSize:尽管NewSize的值被覆盖了,但是实际空间似乎没被覆盖
[@zw_83_83 test]# java -Xms900m -Xmx900m -Xmn400m -XX:NewSize=200m JVMNewSize
running ...
Heap Configuration:
MinHeapFreeRatio = 40
MaxHeapFreeRatio = 70
MaxHeapSize = 943718400 (900.0MB)
NewSize = 209715200 (200.0MB) NewSize被覆盖为200m
MaxNewSize = 419430400 (400.0MB)
OldSize = 5439488 (5.1875MB)
NewRatio = 2
SurvivorRatio = 8
PermSize = 21757952 (20.75MB)
MaxPermSize = 85983232 (82.0MB)
Heap Usage:
PS Young Generation 年轻代加起来是400m,不是200m (实际分配空间没覆盖)
Eden Space:
capacity = 314572800 (300.0MB)
used = 6291472 (6.0000152587890625MB)
free = 308281328 (293.99998474121094MB)
2.000005086263021% used
From Space:
capacity = 52428800 (50.0MB)
used = 0 (0.0MB)
free = 52428800 (50.0MB)
0.0% used
To Space:
capacity = 52428800 (50.0MB)
used = 0 (0.0MB)
free = 52428800 (50.0MB)
0.0% used
PS Old Generation
capacity = 524288000 (500.0MB)
used = 0 (0.0MB)
free = 524288000 (500.0MB)
0.0% used
PS Perm Generation
capacity = 21757952 (20.75MB)
used = 2606792 (2.4860305786132812MB)
free = 19151160 (18.26396942138672MB)
11.980870258377259% used
2、 只覆盖MaxNewSize
[@zw_83_83 test]# java -Xms900m -Xmx900m -Xmn300m -XX:MaxNewSize=400m JVMNewSize
running ...
Heap Configuration:
MinHeapFreeRatio = 40
MaxHeapFreeRatio = 70
MaxHeapSize = 943718400 (900.0MB)
NewSize = 314572800 (300.0MB)
MaxNewSize = 419430400 (400.0MB) 数值被覆盖为400m了
OldSize = 5439488 (5.1875MB)
NewRatio = 2
SurvivorRatio = 8
PermSize = 21757952 (20.75MB)
MaxPermSize = 85983232 (82.0MB)
Heap Usage:
PS Young Generation 实际年轻代累加也是覆盖的400,感觉是取Max值。
Eden Space:
capacity = 314572800 (300.0MB)
used = 6291472 (6.0000152587890625MB)
free = 308281328 (293.99998474121094MB)
2.000005086263021% used
From Space:
capacity = 52428800 (50.0MB)
used = 0 (0.0MB)
free = 52428800 (50.0MB)
0.0% used
To Space:
capacity = 52428800 (50.0MB)
used = 0 (0.0MB)
free = 52428800 (50.0MB)
0.0% used
PS Old Generation
capacity = 524288000 (500.0MB)
used = 0 (0.0MB)
free = 524288000 (500.0MB)
0.0% used
PS Perm Generation
capacity = 21757952 (20.75MB)
used = 2606792 (2.4860305786132812MB)
free = 19151160 (18.26396942138672MB)
11.980870258377259% used
3、 两个都覆盖
[@zw_83_83 test]# java -Xms900m -Xmx900m -Xmn100m -XX:NewSize=200m -XX:MaxNewSize=400m JVMNewSize
Heap Configuration:
MinHeapFreeRatio = 40
MaxHeapFreeRatio = 70
MaxHeapSize = 943718400 (900.0MB)
NewSize = 209715200 (200.0MB)
MaxNewSize = 419430400 (400.0MB)
OldSize = 5439488 (5.1875MB)
NewRatio = 2
SurvivorRatio = 8
PermSize = 21757952 (20.75MB)
MaxPermSize = 85983232 (82.0MB)
Heap Usage:
PS Young Generation 按NewSize和MaxNewSize的最大值分配
Eden Space:
capacity = 314572800 (300.0MB)
used = 6291472 (6.0000152587890625MB)
free = 308281328 (293.99998474121094MB)
2.000005086263021% used
From Space:
capacity = 52428800 (50.0MB)
used = 0 (0.0MB)
free = 52428800 (50.0MB)
0.0% used
To Space:
capacity = 52428800 (50.0MB)
used = 0 (0.0MB)
free = 52428800 (50.0MB)
0.0% used
PS Old Generation
capacity = 524288000 (500.0MB)
used = 0 (0.0MB)
free = 524288000 (500.0MB)
0.0% used
PS Perm Generation
capacity = 21757952 (20.75MB)
used = 2606792 (2.4860305786132812MB)
free = 19151160 (18.26396942138672MB)
11.980870258377259% used
实验3:-XX:NewRatio单独设置有效
[@zw_83_83 test]# java -Xms900m -Xmx900m -XX:NewRatio=2 JVMNewSize
running ...
NewRatio的定义是:New/Old=1:NewRatio
所以,NewRatio是2的话,New占1/3的Heap,也就是300m了。
Heap Configuration:
MinHeapFreeRatio = 40
MaxHeapFreeRatio = 70
MaxHeapSize = 943718400 (900.0MB)
NewSize = 1310720 (1.25MB) 设置NewRatio并不影响NewSize和MaxNewSize的数值,但是影响分配。
MaxNewSize = 17592186044415 MB 此时MaxNewSize的确是默认值无穷大
OldSize = 5439488 (5.1875MB)
NewRatio = 2
SurvivorRatio = 8
PermSize = 21757952 (20.75MB)
MaxPermSize = 85983232 (82.0MB)
Heap Usage:
PS Young Generation 新生代加起来的确是300m
Eden Space:
capacity = 235929600 (225.0MB)
used = 4718608 (4.5000152587890625MB)
free = 231210992 (220.49998474121094MB)
2.0000067816840277% used
From Space:
capacity = 39321600 (37.5MB)
used = 0 (0.0MB)
free = 39321600 (37.5MB)
0.0% used
To Space:
capacity = 39321600 (37.5MB)
used = 0 (0.0MB)
free = 39321600 (37.5MB)
0.0% used
PS Old Generation
capacity = 629145600 (600.0MB)
used = 0 (0.0MB)
free = 629145600 (600.0MB)
0.0% used
PS Perm Generation
capacity = 21757952 (20.75MB)
used = 2606792 (2.4860305786132812MB)
free = 19151160 (18.26396942138672MB)
11.980870258377259% used
[@zw_83_83 test]# java -Xms900m -Xmx900m -XX:NewRatio=8 JVMNewSize
running ...
NewRatio=8,则New占1/9,也就是100m
Heap Configuration:
MinHeapFreeRatio = 40
MaxHeapFreeRatio = 70
MaxHeapSize = 943718400 (900.0MB)
NewSize = 1310720 (1.25MB)
MaxNewSize = 17592186044415 MB
OldSize = 5439488 (5.1875MB)
NewRatio = 8
SurvivorRatio = 8
PermSize = 21757952 (20.75MB)
MaxPermSize = 85983232 (82.0MB)
Heap Usage:
PS Young Generation 年轻代累加和是:100m
Eden Space:
capacity = 78643200 (75.0MB)
used = 1572880 (1.5000152587890625MB)
free = 77070320 (73.49998474121094MB)
2.0000203450520835% used
From Space:
capacity = 13107200 (12.5MB)
used = 0 (0.0MB)
free = 13107200 (12.5MB)
0.0% used
To Space:
capacity = 13107200 (12.5MB)
used = 0 (0.0MB)
free = 13107200 (12.5MB)
0.0% used
PS Old Generation
capacity = 838860800 (800.0MB)
used = 0 (0.0MB)
free = 838860800 (800.0MB)
0.0% used
PS Perm Generation
capacity = 21757952 (20.75MB)
used = 2606792 (2.4860305786132812MB)
free = 19151160 (18.26396942138672MB)
11.980870258377259% used
实验4:-XX:NewRatio被-Xmn覆盖
[@zw_83_83 test]# java -Xms900m -Xmx900m -Xmn400m -XX:NewRatio=8 JVMNewSize
running ...
通过Xmn设置400m,但是NewRatio=8,表示100m,最终是400m还是100呢??
Heap Configuration:
MinHeapFreeRatio = 40
MaxHeapFreeRatio = 70
MaxHeapSize = 943718400 (900.0MB)
NewSize = 419430400 (400.0MB)
MaxNewSize = 419430400 (400.0MB)
OldSize = 5439488 (5.1875MB)
NewRatio = 8 数值上都是按设置的数值,变化了!!!
SurvivorRatio = 8
PermSize = 21757952 (20.75MB)
MaxPermSize = 85983232 (82.0MB)
Heap Usage:
PS Young Generation 新生代的累加和是400m
Eden Space:
capacity = 314572800 (300.0MB)
used = 6291472 (6.0000152587890625MB)
free = 308281328 (293.99998474121094MB)
2.000005086263021% used
From Space:
capacity = 52428800 (50.0MB)
used = 0 (0.0MB)
free = 52428800 (50.0MB)
0.0% used
To Space:
capacity = 52428800 (50.0MB)
used = 0 (0.0MB)
free = 52428800 (50.0MB)
0.0% used
PS Old Generation
capacity = 524288000 (500.0MB)
used = 0 (0.0MB)
free = 524288000 (500.0MB)
0.0% used
PS Perm Generation
capacity = 21757952 (20.75MB)
used = 2606792 (2.4860305786132812MB)
free = 19151160 (18.26396942138672MB)
11.980870258377259% used
分享到:
相关推荐
JVM的内存分为新生代(Young Generation)和老年代(Old Generation)两大部分,用于存放不同生命周期的对象。年轻代主要负责快速回收短期存在的对象,而老年代则存储生命周期较长的对象。新生代又进一步细分为Eden...
JVM内存主要分为年轻代(Young Generation)、老年代(Old Generation)和永久代(Permanent Generation)(在Java 8之后被元空间(Metaspace)取代)。年轻代进一步细分为eden区、survivor区(From和To)以及老年代...
- **PermGen/元空间大小**:在Java 8之前,`XX:PermSize`和`XX:MaxPermSize`用于设置永久代大小;在Java 8及以上,元空间大小由系统决定,但可以通过操作系统参数限制。 - **线程栈大小**:`-Xss`参数设定每个...
-XX:MaxPermSize=256m:设置持久代(PermGen)的大小为256MB,持久代用于存储类的元数据。 -Xms和-Xmx:分别设置JVM启动时的初始堆大小和最大堆大小。为了提升性能,建议将这两个值设置相同,以避免动态内存分配。 -...
1. **内存管理**:JVM内存分为堆内存(Heap)和非堆内存(Non-Heap),包括年轻代(Young Generation)、老年代(Tenured Generation)以及永久代(PermGen,Java 8后被元空间(Metaspace)取代)。了解每个区域的...
- **内存设置**:合理设置堆内存大小,避免频繁的垃圾回收。 - **垃圾回收器选择**:根据应用特性选择合适的垃圾回收器。 - **监控工具使用**:使用JVisualVM、JConsole等工具监控JVM的运行状态,识别性能瓶颈。 - *...
3. **-XX:PermSize**:表示JVM永久代(PermGen space)初始大小。例如`-XX:PermSize=64M`表示JVM永久代初始大小为64MB。注意,从JDK 8开始,永久代被元空间(Metaspace)所替代。 4. **-XX:MaxPermSize**:表示JVM...
它打破了传统JVM内存区域的划分,将堆内存划分为多个大小相等的Region,每个Region既可以包含年轻代对象,也可以包含老年代对象。G1采用了混合收集(Mixed GC)策略,能够在一次GC过程中同时回收年轻代和老年代的...
这类问题通常是由于 JVM(Java 虚拟机)配置不当导致的,特别是 PermGen 和 Heap 的大小设置不合理。PermGen 是指永久代空间,用于存储 Class 文件的元数据信息;而 Heap 则是 Java 应用程序运行时的主要内存区域。...
对于HotSpot虚拟机而言,这部分区域被称为“永久代”(PermGen space),而在JVM 8之后,已经被“元空间”(Metaspace)所替代,其物理内存空间不再受堆大小限制,而是由系统的实际可用内存决定。 #### 2. 堆 堆是...
堆的大小可通过-Xmx(最大堆内存)、-Xms(初始堆内存)设置。堆中还可以细分为新生代(Young Generation)、老年代(Old Generation)等区域。 2. 方法区(Method Area):用于存储已经被虚拟机加载的类信息、...
其中,堆内存是最大的一部分,包括新生代(Young Generation)、老年代(Old Generation)和持久代(Perm Gen,Java 8后被元空间Metaspace取代)。通过 `-Xms` 和 `-Xmx` 设置初始和最大堆大小, `-XX:NewRatio` ...
1. **调整PermGen Space大小**:通过修改JVM启动参数`-XX:PermSize`和`-XX:MaxPermSize`来增加PermGen Space的初始大小和最大限制。例如,将`-XX:PermSize=64M`和`-XX:MaxPermSize=128m`添加到Tomcat的启动脚本中。 ...
- **PermGen/Metaspace Overflow**:持久代/元空间溢出,通常由于过多的类或大型静态变量引起,可通过增大相应区域大小或限制类加载。 9. **JIT编译器(Just-In-Time Compiler)**: - **HotSpot** JVM包含C1和C2...
堆可以细分为新生代(Young Generation)、老年代(Tenured Generation)和持久代(Perm Gen,Java 8后已被元空间取代)。 5. **方法区(Method Area)** 也被称为永久代,存储类信息、常量、静态变量以及编译后的...
堆中的内存可以是固定大小,也可以是可扩展的,其大小可以通过JVM参数进行设置。 - **栈(Stack)**:存储局部变量和方法调用的状态,线程私有。每当方法执行时,JVM就会在栈中创建一个栈帧(Stack Frame)用于存储...
一般而言,年轻代的大小设置为整个堆内存的1/3至1/4比较合适。 - **示例**:`java -Xmn2g ...` - **说明**:年轻代的大小会影响其内部的Eden区和Survivor区的比例分配。可以通过-XX:NewRatio和-XX:SurvivorRatio来...
方法区主要用于存放类信息、常量、静态变量等,它在JDK中对应的是持久代(Permanent Generation,PermGen),可以通过JVM参数-XX:PermSize和-XX:MaxPermSize来指定其最小值和最大值。由于方法区的垃圾收集并不频繁,...