jvm相关总结

一. jvm的内存模型图

二.jvm的启动流程.

三.Java类加载过程

一个Java文件从编码完成到最终执行包括两个过程, 编译(Javac xxx.java)生成xxx.class 文件,  运行(Java xxx)就是将生成的xxx.class文件交给虚拟机运行.而我们说的的加载过程就是虚拟机将xxx.class文件中的类的信息加载到内存中.并运行解析生成的Class对象的过程.

例子: 当虚拟机运行到某段代码的时候遇到了 xxx 但是此时内存中没有xxx 的相关信息,于是虚拟机就会到相应的 xxx.class文件中寻找 xxx的类信息, 并加载到内存中,这就是我们常说的类加载过程,虚拟机不是一开始就将所有的类加载到内存中,而是在第一次遇到需要加载的类的时候才会进行加载,并且只加载一次.

其中类加载过程包括 1.加载 2.连接 3.初始化三个过程

当一个类加载器接收到一个类加载的任务时,不会立即展开加载,而是将加载任务委托给它的父类加载器去执行,每一层的类都采用相同的方式,直至委托给最顶层的启动类加载器为止。如果父类加载器无法加载委托给它的类,便将类的加载任务退回给下一级类加载器去执行加载。
双亲委托模型的工作过程是:如果一个类加载器收到了类加载的请求,它首先不会自己去尝试加载这个类,而是把这个请求委托给父类加载器去完成,每一个层次的类加载器都是如此,因此所有的加载请求最终都应该传送到顶层的启动类加载器中,只有当父类加载器反馈自己无法完成这个加载请求(它的搜索范围中没有找到所需要加载的类)时,子加载器才会尝试自己去加载。
使用双亲委托机制的好处是:能够有效确保一个类的全局唯一性,当程序中出现多个限定名相同的类时,类加载器在执行加载时,始终只会加载其中的某一个类。
使用双亲委托模型来组织类加载器之间的关系,有一个显而易见的好处就是Java类随着它的类加载器一起具备了一种带有优先级的层次关系。例如类java.lang.Object,它存放在rt.jar之中,无论哪一个类加载器要加载这个类,最终都是委托给处于模型最顶端的启动类加载器进行加载,因此Object类在程序的各种加载器环境中都是同一个类。相反,如果没有使用双亲委托模型,由各个类加载器自行去加载的话,如果用户自己编写了一个称为java.lang.Object的类,并放在程序的ClassPath中,那系统中将会出现多个不同的Object类,Java类型体系中最基础的行为也就无法保证,应用程序也将会变得一片混乱。如果自己去编写一个与rt.jar类库中已有类重名的Java类,将会发现可以正常编译,但永远无法被加载运行。
双亲委托模型对于保证Java程序的稳定运作很重要,但它的实现却非常简单,实现双亲委托的代码都集中在java.lang.ClassLoader的loadClass()方法中,逻辑清晰易懂:先检查是否已经被加载过,若没有加载则调用父类加载器的loadClass()方法,若父加载器为空则默认使用启动类加载器作为父加载器。如果父类加载器加载失败,抛出ClassNotFoundException异常后,再调用自己的findClass方法进行加载。

 

四.jvm常用参数和工具参数.

1) 以-X开头的都是非标准的(这些参数并不能保证在所有的JVM上都被实现),而且如果在新版本有什么改动也不会发布通知。

2)以-XX开头的都是不稳定的并且不推荐在生产环境中使用。这些参数的改动也不会发布通知。不建议在生产上使用

官方文档地址:    http://www.oracle.com/technetwork/java/javase/tech/vmoptions-jsp-140102.html

注意格式:当进行参数设定的时候, -Xmn2G 就能进行生效, 但是 -XX:NewSize=2G 才能生效,

区分大小写.

产看非标转的命令是:java -X

jvm参数总结
参数名称备注
-XX:NewSize=1024m设置年轻代初始值为1024M(优先级比-Xmn高)应该小于 -Xms的值
-XX:MaxNewSize=1024m设置年轻代最大值为1024M。(优先级比-Xmn高)这个值应该小于 -Xmx的值
-Xmn2g 在整个堆内存大小确定的情况下,增大年轻代将会减小年老代,反之亦然。此值关系到JVM垃圾回收,对系统性能影响较大,官方推荐配置为整个堆大小的3/8,包括Eden 和Survivor,从jdk1.4开始使用
-XX:NewRatio=4设置年轻代(包括1个Eden和2个Survivor区)与年老代的比值。表示年轻代比年老代为1:4
-XX:SurvivorRatio=6设置年轻代中Eden区与Survivor区的比值。系统默认是8,根据经验设置为6,则2个Survivor区与1个Eden区的比值为2:6,一个Survivor区占整个年轻代的1/8
-XX:PermSize表示非堆区初始内存分配大小,其缩写为permanent size(持久化内存)但是1.8取消了PermGn 用Meta Space取代了.
-XX:MaxPermSize表示对非堆区分配的内存的最大上限,该参数设置的区域是类型新, 静态变量, 常量.如果这些信息较多会造成OutOfMemaryError
-XX:MaxTenuringThreshold=0设置垃圾最大年龄(在年轻代的存活次数)。如果设置为0的话,则年轻代对象不经过Survivor区直接进入年老代。对于年老代比较多的应用,可以提高效率;如果将此值设置为一个较大值,则年轻代对象会在Survivor区进行多次复制,这样可以增加对象再年轻代的存活时间,增加在年轻代即被回收的概率。根据被海量访问的动态Web应用之特点,其内存要么被缓存起来以减少直接访问DB,要么被快速回收以支持高并发海量请求,因此其内存对象在年轻代存活多次意义不大,可以直接进入年老代,根据实际应用效果,在这里设置此值为0!
-XX:+UseConcMarkSweepGC设置年老代为并发收集。CMS(ConcMarkSweepGC)收集的目标是尽量减少应用的暂停时间,减少Full GC发生的几率,利用和应用程序线程并发的垃圾回收线程来标记清除年老代内存,适用于应用中存在比较多的长生命周期对象的情况。
 -Xss<size> JDK5.0以后每个线程栈大小为1M,之前每个线程栈大小为256K。应当根据应用的线程所需内存大小进行调整。在相同物理内存下,减小这个值能生成更多的线程。但是操作系统对一个进程内的线程数还是有限制的,不能无限生成,经验值在3000~5000左右。需要注意的是:当这个值被设置的较大(例如>2MB)时将会在很大程度上降低系统的性能。
 -Xms<size>  设置初始 Java 堆大小,通常为操作系统可用内存的1/64大小即可,但仍需按照实际情况进行分配。有可能真的按照这样的一个规则分配时,设计出的软件还没有能够运行得起来就挂了
-Xmx<size> 设置最大 Java 堆大小,通常为操作系统可用内存的1/4大小。但是开发过程中,通常会将 -Xms 与 -Xmx两个参数的配置相同的值,其目的是为了能够在java垃圾回收机制清理完堆区后不需要重新分隔计算堆区的大小而浪费资源,一般建议堆的最大值设置为可用内存的最大值的80%
-XX:ParallelGCThreads=8配置并行收集器的线程数,即同时8个线程一起进行垃圾回收。此值一般配置为与CPU数目相等

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

-Xmn

-XX:NewSize/-XX:MaxNewSize

-XX:NewRatio

3组参数都可以影响年轻代的大小,混合使用的情况下,优先级是什么?
如下:
高优先级:-XX:NewSize/-XX:MaxNewSize
中优先级:-Xmn(默认等效 -Xmn = -XX:NewSize = -XX:MaxNewSize=?)
低优先级:-XX:NewRatio
推荐使用-Xmn参数,原因是这个参数简洁,相当于一次设定 NewSize/MaxNewSIze,而且两者相等,适用于生产环境。-Xmn 配合 -Xms/-Xmx,即可将堆内存布局完成。
-Xmn参数是在JDK 1.4 开始支持。

FullGC的触发条件: 1.年老代(tenured)写满 2.持久代(permanent)写满 3.System.gc() 被显示调用. 4.上一次GC之后Heap的各个区域分配策略动态变化.

 

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值