`
囧囧有神
  • 浏览: 204706 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

JVM垃圾回收知识汇总

    博客分类:
  • java
qu 
阅读更多

什么是垃圾回收

  • java程序运行期间生成新对象,加载类文件都需要占用内存,不同对象从被创建,使用,存储到最后使用完毕被销毁都有一个完整的生命周期,java程序开发人员实际上只需要负责对象的创建使用,对象的销毁回收由虚拟机自动完成,对象的回收过程就是垃圾回收

怎么来做垃圾回收

  • jvm运行期间使用的内存包括堆内存,创建线程使用的vm栈内存,存储方法,类,常量池使用的永久代内存,堆外内存(direct buffer),开发人员使用的是heap(堆内存),也是重点需要管理的区域
  • 由于不同对想的生命周期长短不同,因此需要将整块堆内存分成不同的区域,E,S1,S2,O,Eden区存放生命周期最短的对象,S区中等长度,Old区存长生命周期对象,因此对不同的区域启用不同的回收算法。
  • 对象在堆的各个区域移动过程如下:E区满了进行一轮回收,剩下的晋升到空的S区,同时将非空的S区进行回收,剩下的也全部拷贝到空S区,将达到存活时间的对象晋升进入O区。
  • 为什么会有两个S区,主要是为了处理回收碎片,E区满了回收之后所有对象拷贝进入S区,S区也会被回收,因此S区面临三种选择:1)整理并压缩碎片,空出整块的内存区域,2)将E区晋升上来的对象适配到S区中的碎片空间中;3)设置两块S区,将E区和非空S区的存活对象全部合并拷贝进入空S区;最终SUN选择第三种方法,从直觉上考虑直接合并拷贝应该是效率最高的,相当于用空间换时间 

垃圾回收参数

其中 -Xmx 控制了 E S1 S2 O 这四个区的总大小,-XX:PermSize 和 -XX:MaxPermSize控制了PermGen的大小,两块的大小独立设置,因此总的堆内存大小 E+S1+S2+O+P= -Xmx + -XX:MaxPermSize

 

-Xms 初始堆大小,MinHeapFreeRatio参数可以调整空闲堆内存小于40%时候JVM会扩充堆内存到最大设置值

-Xmx 最大堆大小,MaxHeapFreeRatio参数可以控制空闲堆内存大于70%时候JVM减少堆知道最小值

-Xmn 新生代大小(E + S1 +S2),SUN推荐的大小是整个堆大小的3/8,增大这个值会减小O区的大小

-XX:PermSize 初始永久带大小

-XX:MaxPermSize 最大永久带大小,这个值设置推荐是系统P区基本稳定下来的量的1.5倍左右

-XX:SurviorRatio E区和S区的比例,默认是8,

-Xss: 每个线程的堆栈大小,jdk1.5之前是256,之后是1M。在物理内存不变的情况下减小这个值能生成更多的线程。一个进程内的线程最大数经验值推荐在3000-5000左右,调用栈不深的应用128K差不多够用了,大一点的差不多256K,具体的值还需要严格的测试。

 

常见的垃圾回收器

Serial回收器:jvm历史最悠久的回收器,jdk在client模式下默认的回收器,特点是启动回收的时候需要停止一切用户线程,对于小内存的应用回收效率高,不适合对响应时间要求高,大内存的应用;

Parallel回收器:并行回收相当于Serial串行回收器的多线程版,回收的时候还是需要stop the word,只是启用多线程回收让停顿时间缩短,满足对用户响应时间比较看重的应用,比如WEB应用。

CMS回收:也叫并发回收,针对Old区的回收分成6个阶段:

初始标记(CMS initial mark)

并发标记(CMS concurrent mark)

并发预清理(CMS-concurrent-preclean)

重新标记(CMS remark)

并发清除(CMS concurrent sweep)

并发重置(CMS-concurrent-reset)

初始标记和重新标记需要S-T-W,其他步骤都是和用户线程一起运行,初始标记只是把从GC Root能直接关联到的对象快速标记出来,重新标记标记是对在初始标记之后新产生的可回收对象补充做一轮标记,并发标记是GC Root Tracing,花的时间比较长。

 

CMS的young区默认使用ParNew的并发回收算法,也不会S-T-W,CMS优点众多,把JVM停顿的时间竟可能缩短,也有几个缺点:1)在回收的过程中用户线程继续运行的方式可能会发生回收还没做完但是没足够空间满足应用对内存的申请或者没有足够空间放下新晋升到Old区的对象,导致 发生 conncurrent mode failed,触发一次串行的FGC,大内存的FGC停顿时间会相当长,比较要命,因此要妥善设置CMS触发阀值,和Old区的大小,提前预留足够的Old区空间;2)同用户线程一块运行会额外占用一些CPU资源;3)产生内存碎片,启用碎片压缩的情况下在FGC事后会进行碎片整理

 

DirectBuffer的垃圾回收

  • 堆外内存的好处是减少数据拷贝次数,减少对heap堆垃圾回收的影响
  • java中的类DirectBuffer只是个堆外内存的引用,存储了实际内存引用地址和大小,封装了申请和回收的操作,内存的申请和回收实际上是调用native方法类似 malloc和calloc的方法;
  • DirectBuffer本身的对象大小很小,但是关联的堆外内存可能非常大,因此使用它的风险在于如果没好好回收DirectBuffer,明明堆内还很空,但是整个系统内存可能已经被耗尽了,因此JVM使用XX:MaxDirectMemorySize来约束申请的堆外内存量,防止由于使用不当,一个java进程搞挂整台机器
  • DirectBuffer的回收机制也很特殊,因为DirectBuffer这个java对象和关联的堆外内存实际上是处于两块不同区域,它通过关联一个PhantomReference,当DirectBuffer对象没有外部强引用之后其本身会被塞进一个ReferenceQueue,这个特殊实现的Queue里头有个后台线程一直扫描队列,把队列中的对象所关联的堆外内存释放掉,这种机制的好处是JVM对于内存的管理统一了,堆外这种异类就用异步的方式来特殊实现来回收释放;
  • 堆外内存在申请的时候如果不够就会调用System.gc触发FGC,并且为了及时回收堆外内存也会经常手工调用System.gc,因此设置这个参数也很重要-XX:+ExplicitGCInvokesConcurrent,把System.gc转换成一次CMS的执行,提高效率

垃圾回收日志格式

基本上都是这种格式:回收前区域占用的大小->回收后区域占用的大小(区域设置的大小),占用的时间,

具体的网上找下文档

 

垃圾回收调优处理过程--观察

  1. 收集当前java进程的内存相关启动参数,观察系统日志有没有OOM异常,观察GC日志,关注FGC以及concurrent mode failed 或者 promotion failed异常,以及GC监测工具观察系统内存使用状况;
  2. minor gc执行频率,如果执行非常频繁就要关注内存大小是否够用,程序代码写的质量是否不高;
  3. FGC执行频率,每次FGC回收效果如何,这个现象要考察内存大小是否够用,如果每次FGC效果差需要重点怀疑内存泄露;
  4.  minor gc 和 survior回收效果如何,每次会有多少对象晋升到老年代,如果回收效果差,要考察系统使用内存情况(heap dump)或者Young区大小是否够用,系统是频繁产生大对象;
  5. CMS频率是否执行过高,对于这一条可以检查下触发CMS的所有条件,包括:1)old区占用量是否导到达触发CMS阀值;2)是否开启了JVM根据成本计算自主决定CMS是否启用;3)永久带回收是否打开,并且永久带占用是否达到回收阀值;4)是否设置了ExplicitGCInvokesConcurrent,由外部system.gc触发

垃圾回收调优处理过程--设定调优目标

根据第一步观察到的状况来设定调优目标:

  1. OOM--调大内存占用,MAT分析内存详情,排除内存泄露
  2. 降低minor gc 频率活minor gc执行时间
  3. 降低 fgc 频率或 fgc 执行时间

调整的效果可以通过 jstat 的 gcutil来观察调优目标是否达到

 

垃圾回收调优处理过程--常用策略的选择

  1. 降低FGC频率的办法:1)加大内存以及Old区;2)观察每次survior回收后是否大量晋升到Old,可以尝试调大S区,或者调大S区存活次数;3)调优程序,控制缓存等长生命周期对象的使用量
  2. 降低minor gc频率的办法:1)加大Eden区;2)用CMS并发回收器;3)增加并行收集的线程数;4)升级CPU;
  3. 降低minor gc回收时间或old 回收时间:1)减小区域占用内存大小;2)对于CMS,调小CMS触发阀值;3)换更多更牛逼的CPU;4)优化代码

 JDK 7,JDK8中的新特性:G1垃圾回收器

 G1 GC是jdk 7 对JVM GC算法做了一次重大升级,当初计划用来替换CMS。JDK 8中进一步对G1做了优化,去掉了永久带。G1的目标是减少因为GC带了的系统停顿。

G1将Java堆内存空间划分成一块块等大的区域(region),每个区域都是一段连续的内存空间,E,S,O区将不再固定,而是可以利用任意的空白区块。小区快带来的好处是后台回收线程在扫描可回收对象时候可以优先清理那些包含更多可回收对象的区块,用相同的停顿时间回收更多的垃圾,总体提高回收效率,缩短总体停顿时间。和CMS比有下面一些优势:

  • G1通过将内存空间分成区域(Region)的方式避免内存碎片问题
  •  Eden, Survivor, Old区不再固定、在内存使用效率上来说更灵活
  • 可以预设停顿时间控制GC停顿对系统响应的影响程度
  • G1在回收内存后会马上同时做合并空闲内存的工作、而CMS默认是在STW(stop the world)的时候做
  • G1会在Young GC中使用、而CMS只能在O区使用

 

 

 

分享到:
评论

相关推荐

    JVM入门实战/arthas实战/垃圾回收算法/垃圾回收器/jvm内存模型分析

    第四节:垃圾回收算法 1.1标记清除算法 1.2复制算法 1.3 标记整理(标记压缩)算法 第五节:垃圾回收器 1.1Serial/Serial Old收集器 1.2 ParNew收集器 1.3Parallel Scavenge收集器 1.4Parallel Old收集器 1.5CMS...

    JVM超详细知识点汇总.txt

    (原创)JVM超详细知识点汇总,汇总了JVM内存模型,字节码,垃圾回收器,类加载器,JVM调优等众多非常详细的知识点。能够助你能深入完全的掌握JVM。

    JVM 精华知识点汇总1

    前言文章对 JVM 内存区域分布、JVM 内存溢出分析、JVM 垃圾回收算法/垃圾收集器、JVM 性能调优工具及技巧、类加载等部分做了详细描述。用XMind画了

    JVM GC问题和垃圾回收器讲解.pdf

    有关JVM垃圾回收器讲解,详细讲解了10种垃圾回收器的详细知识点,是自己面试时候自己进行总结的,费劲了心血,感谢各位的下载支持

    简单理解JVM垃圾回收

    文章目录如何判断一个对象是垃圾垃圾回收算法分代收集算法垃圾收集器相关知识总结 如何判断一个对象是垃圾 我们都知道了当堆中的区域没有足够内存去存放对象时就会触发垃圾回收,那么如何来判断一个对象是不是垃圾呢...

    JVM调优总结(4)分代垃圾回收Java开发Java经验技

    JVM调优总结(4)分代垃圾回收Java开发Java经验技巧共10页.pdf.zip

    JVM与性能优化知识点整理.pdf

    JVM常见知识点总结。非常好的JVM资料,主要有五大章节 JVM内存区域划分 JVM执行子系统 垃圾回收器和内存分配策略 编写高效优雅Java程序 性能优化

    jvm:jvm知识总结

    java虚拟机知识总结学习java虚拟机的脆弱原理,JVM的整体结构如下内存与垃圾回收字节码与类的加载性能监控和调优

    JVM笔记资料压缩文件

    jvm笔记 1、jvm总体架构.pdf 2、堆内存内部结构.pdf 3、有关内存的常用配置参数.pdf ...5、jvm里的垃圾回收机制.pdf 6、jvm优化知识点升级和配置总结.pdf 7、Tomcat调优实战.pdf 8、动态查看JVM内存的工具.pdf

    JVM面试复习.pdf

    JVM基础知识点讲解总结 包括JVM的内存结构、Java线程间通信、JMM底层原理、垃圾回收机制与双亲委派机制等等

    深入理解JVM内存结构及运行原理全套视频加资料.txt

     第34讲 垃圾回收-判断对象是否存活算法-可达性分析法详解 00:07:09  第35讲 垃圾回收算法-标记清除算法 00:04:36  第36讲 垃圾回收算法-复制算法 00:14:35  第37讲 垃圾回收算法-标记整理算法和分代收集...

    JVM虚拟机内容导图.xmind

    JVM虚拟机各知识点总结整理, 包括java虚拟机概念、堆、栈、方法区、垃圾回收概念、算法及分代转换、垃圾收集器参数配置、算法实现等各方面内容,每个点都有详细的备注描述介绍

    JAVA核心知识点整理.zip

    JVM 是可运行 Java 代码的假想计算机 ,包括一套字节码指令集、一组寄存器、一个栈、 一个垃圾回收,堆 和 一个存储方法域。JVM 是运行在操作系统之上的,它与硬件没有直接 的交互。 3. JAVA 集合 集合类存放于 ...

    Java面试资料总结

    此Java面试资料总结囊括JVM垃圾回收,JVM内存模型以及java基础知识笔试和java面试宝典,更有SpringMVC经典面试题,MyBatis相关知识,剑指offer名企面试笔试算法题,MYSQL性能优化以及索引和锁相关知识。

    Notes:This is a learning note | Java基础,JVM,源码,大数据,面经

    jvm垃圾收集机制与内存分配策略 jvm类加载机制 Java的内存模型 锁优化 Think In Java Java容器 Java并发 Java Concurrency in Practice 对象的共享 对象的组合 基础构建模块 JavaGC监控与优化 垃圾回收机制 垃圾回收...

    java常见面试题汇总(附答案).pdf

    垃圾回收:通过自动垃圾回收机制管理内存,降低了内存泄漏的风险。 强类型:要求严格的数据类型定义,减少了类型转换错误。 多线程:支持多线程编程,提高了程序的并发性能。 开源:Java 的开源性质促进了生态系统的...

    JAVA笔试总结 -- 非常全面

    native,transient,volatile,strictfp,CMM,synchronized,java socket,压缩与解压缩,多线程,垃圾回收算法,JVM ClassLoader,IO流,反射机制,JNDI, GUI布局管理器,JMS, Java Mail, JNDI reference,java事件处理...

    Java 排序算法知识点总结.zip

    Java是一种高性能、跨平台的面向...自动内存管理(垃圾回收): Java具有自动内存管理机制,通过垃圾回收器自动回收不再使用的对象,使得开发者不需要手动管理内存,减轻了程序员的负担,同时也减少了内存泄漏的风险。

    Java知识点总结,面试必备.zip

    Java是一种高性能、跨平台的面向...自动内存管理(垃圾回收): Java具有自动内存管理机制,通过垃圾回收器自动回收不再使用的对象,使得开发者不需要手动管理内存,减轻了程序员的负担,同时也减少了内存泄漏的风险。

    corejava基础重要知识点总结

    糟粕:手动垃圾回收 运算符重载 指针 思想简单:面向对象的思想 = OO思想 面向过程:需要人站在计算机的角度去思考问题 面向对象:需要人拿着代码模拟实现生活 类:一组类型相同事物高度抽象之后的集合概念 ...

Global site tag (gtag.js) - Google Analytics