zoukankan      html  css  js  c++  java
  • 浅谈Java堆内存分代回收

    1.概述

    与C++不同的是, 在Java中我们无需关心对象占用空间的释放, 这主要得益于Java中的垃圾处理器(简称GC)帮助我们自动的进行对象占用空间的释放.

    下面我们带着几个问题来学习:

    • 堆内存是如何分代的?
    • 各分代之间是如何配合工作的?

    2.堆内存是如何分代的

    用一张图片来描述(面积大小不代表实际占用空间大小)

    堆内存分为: 年轻代(Young) + 老年代(Old), 年轻代又分为: Eden区 + Survivor区 * 2.

    通常年轻代中的各区比值为: Eden区: Survivor0 : Survivor1 = 8:1:1

    要尽可能的让对象不进入Old区.

    S0和S1默认情况下会动态的自动调整大小, 可以使用-XX:UseAdaptiveSizePolicy来关闭动态调整.

    3.各分代之间是如何配合工作的

    以一个对象的在每个区之间的复制来描述这个问题, 我们假定这个对象一直存活着.

    当我们写一段如下代码时

    User user = new User();
    

    user对象首先被放入到Eden区, 当Eden区满的时候会发生第一次Minor GC, 这时垃圾收集器会在S0和S1中随机选择一个区(假设选中了S0)来存放Eden区剩余存活的对象. 当Eden区再次满的时候会发生第二次Minor GC, 这时垃圾收集器会把Eden区存活的对象 + S0中存活的对象复制到S1中, 当Eden区再次满的时候会发生第三次Minor GC, 这时垃圾收集器会把Eden区存活的对象 + S1中存活的对象复制到S0中, 如此循环复制.

    那么对象什么情况下会进入到Old区?

    • Eden区满时, 在对象将要进入S0或S1中时, 如果S0或S1存放不下Eden区中某个对象时, 这个对象将被复制到Old区.
    • 如果一个对象在S0和S1中经历了指定次数(-XX:MaxTenuringThreshold=15)的复制之后, 会被复制到Old区.

    顺便说一下: 年轻代垃圾回收使用 复制算法, 老年代回收使用 标记清除算法.

  • 相关阅读:
    Python 文件的输入与输出
    php获取客户端真实ip
    php设计模式(3)-观察者模式
    php设计模式(2)-单例模式
    php设计模式(1)-工厂模式
    设计模式
    设计模式-观察者模式
    include和require的区别
    php分页类
    反向Ajax,第5部分:事件驱动的Web开发
  • 原文地址:https://www.cnblogs.com/wuqinglong/p/10155757.html
Copyright © 2011-2022 走看看