【JVM】Java虚拟机内存模型 和 GC

java 虚拟机内存模型主要有三大部分

  1. 运行数据区
  2. 执行引擎
  3. 本地方法接口

我们平常需要了解和关注的主要是有关运行数据区的详细信息
运行数据区主要有五大部分

  1. 栈(虚拟机栈是JAVA方法执行的内存模型,包括多个栈帧,每个栈帧包括局部变量表,操作栈,动态连接,返回地址等)
  2. 堆(存储对象)
  3. 程序计数器
  4. 本地方法栈
  5. 方法区(元数据区 1.8?)
    https://zhuanlan.zhihu.com/p/161994662

清楚了内存模型,就可以开始了解GC

怎么定义垃圾

  1. 引用计数法
    在堆中的对象会有一个引用标志位,当改对象实例被引用一次,改标志位+1 ,当引用释放(主动或被动),该引用 -1 。
    当值为0时,则视为改对象实例无人引用,可作为垃圾
    缺点:存在循环引用的情况会导致内存泄漏。
  2. 可达性算法
    从GC root开始进行图状的遍历,从GC root 开始,通过引用可以到达的对象实例是活跃对象实例,其余的则视为垃圾
    可作为GC root的变量(对象):
    虚拟机栈中局部变量表中变量(引用的对象)
    方法区(元空间)中的常量(引用的对象)
    方法区(元空间)中类静态变量(引用的对象)
    本地方法栈中JNI引用的对象
    https://segmentfault.com/a/1190000038405609

如何清理垃圾

  1. 标记-清理
    直接标了直接请
    缺点:内存空间碎片化
  2. 标记-清理
    标完之后将活着的整理到一起,清理剩余空间
    缺点:资源消耗大,时间慢
    3.复制-清理
    将活着的一起复制到另一个内存区域
    清理之前的

组合拳(第一弹):
eden区
对象产生的地方当eden区满后 ,则会触发minor GC
survival from 区
当minorGC触发时,会通过可达性算法找出eden区以及当前survival 区的存活对象
将其全部移动到survival 0区
当survival 0 区满时,则会在进行一次minorGC , 将当前的移动到 survival 1区

每进行一次移动,对象的年龄就会增加1
默认15 次之后, 会将该对象移动到老年代
可以通过参数 -XX:MaxTenuringThreshold (阈值)来设置
老年代:
采用标记-清理算法
如果老年代满,则会出发一次full GC
fullGC 包含 minor GC (年轻代)和mayjor GC(老年代)

STW
stop the word
进行垃圾回收时,jvm需要所有进程达到安全点后暂停所有用户线程,称为 stw
安全点:
方法调用时,循环跳转时,异常跳转时

组合拳第二弹:
serial 垃圾收集器(复制算法) -XX: UseSerialGC
单线程收集器,年轻代收集器,收集时造成STW,暂停所有用户线程
client jvm 默认垃圾收集器
parnew 垃圾收集器(复制算法) -XX: UseParNewlGC
并行垃圾处理器 , 年轻代收集器,收集时造成STW,暂停所有用户线程

parallel scavange垃圾收集器(复制算法) -XX: UseParallelGC
并行垃圾处理器 ,年轻收集器,更注重系统吞吐量(用户代码运行时间/用户+垃圾收集器运行时间)
多核下有优势,server jvm 默认垃圾收集器,适合计算量高的后端
可以通过 -XX : UseAdaptiveSizePolicy 来使其采用自适应优化

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值