一、概述
JVM,全称Java Virtual Machine,就是java虚拟机,是一台虚构的机器,或者软件,用来执行虚拟计算指令;jvm是一种程序虚拟机,执行的是 .class字节码文件里面的字节码指令,现在使用最多的是java虚拟机是Hotspot虚拟机。
二、JVM 的结构
由类加载子系统(ClassLoader)、运行时数据区、执行引擎、内存回收系统这四个部分组成。
源代码文件被编译成.class字节码文件,被类加载器加载到jvm中,执行引擎解释执行字节码文件,调用本地方法接口,执行底层C语言的方法。jvm使用方法区class类为元数据模板创建类的实例(对象)。
三、JVM参数
3.1 堆内存分配参数
-XX 开头的是jvm系统级别的配置参数设置,非-XX打头的是应用级别的参数设置
-XX:+<option> 是开启option参数
-XX:-<option> 是关闭option参数
-XX:+<option>=<value> 是把option参数的值设为value
GC调试参数
-XX:+PrintGC 当发生GC时候就打印GC日志
-XX:+UseSerialGC 配置串行回收器
-XX:+PrintGCDetails 打印GC详细信息,包含运行时数据各个区的情况
-XX:ParallelGCThreads=10 垃圾回收并行线程数=10
-XX:CMSMaxAbortablePrecleanTime=5000 CMS GC的回收超时时间,避免GC时间太久
-XX:+HeapDumpOnOutOfMemoryError OOM时生成 dump文件
堆大小设置
-Xms: 设置初始堆大小
-Xmx: 设置最大堆大小
-Xmn 设置年轻代堆大小
-XX:SurvivorRatio=value 设置新生代的 eden区和s区的比例 = eden/s0 = eden/s1
方法区或永生代相关设置
-XX:PermSize=64MB 最小尺寸,初始分配
-XX:MaxPermSize=256MB 最大允许分配尺寸,按需分配
四、JVM垃圾回收
4.1回收过程
新生代的Survivor 区分为2块大小相等、可以互换角色的区域,分别是from区和to区,又叫S0和S1区:
对象刚实例化,放到eden区,经过一次垃圾回收(minor gc),会把存活的对象移动到Survivor
from (S0)区:
再经历一次minor gc,这个对象任然存活的话,被复制到Survivor to(S1)区,此对象年龄 age+1,S0空间被回收,此时,将S0和S1区进行互换,存活的对象在S0:
以此类推,再一次minor gc,此对象任然存活,继续age++,回收S0,交换角色,一直到对象age达到15,会进入老年代:
当下次老年代内存也不够,会触发major gc
4.2回收算法
垃圾回收在新生代的时候,会用到复制算法:
在老年代时,有可能会用到标记-清楚算法(mark-sweep)算法:
或者标记-整理(mark-Compact)算法:
五、JVM调优
java -Xmx2048m -Xms2048m -Xss128k -XX:NewRatio=2 -XX:SurvivorRatio=6
-XX:MaxPermSize=100m -XX:MaxTenuringThreshold=20
-XX:NewRatio=2:设置年轻代(包括Eden和两个Survivor区)与年老代的比值(除去持久代)。设置为3,则年轻代与年老代所占比值为1:3,年轻代占整个堆栈的1/4
-XX:SurvivorRatio=6:设置年轻代中Eden区与Survivor区的大小比值。设置为6,则两个Survivor区与一个Eden区的比值为2:6,一个Survivor区占整个年轻代的1/8
-XX:MaxPermSize=100m:设置持久代大小为100m。
-XX:MaxTenuringThreshold=20:设置垃圾最大年龄。如果设置为0的话,则年轻代对象不经过Survivor区,直接进入年老代。对于年老代比较多的应用,可以提高效率。如果将此值设置为一个较大值,则年轻代对象会在Survivor区进行多次复制,这样可以增加对象在年轻代的存活时间,增加年轻垃圾回收概率,比如一次网络请求返回响应,这样的很多临时对象,适用此。