JVM垃圾回收

2021-11-28  本文已影响0人  小明阿婆

JVM (java虚拟机)

参考文献:

Java 虚拟机(JVM )- 内存与垃圾回收篇概述哔哩哔哩bilibili

Java开发必须掌握的线上问题排查命令-HollisChuang's Blog

JVM

JVM:java虚拟机,执行JAVA字节码的虚拟计算机。

是否遇到过这些问题?

- 运行着的线上系统突然卡死,系统无法访问,甚至直接OOM
- JVM GC问题
- JVM参数



所有java程序都运行在JVM上

JVM特点

JVM的整体结构

jvm整体架构图文详解等待、的博客-CSDN博客jvm架构





堆 heap

对进程独立,对线程为共享

栈存放对象、指针,而堆空间存放实例

基于分代收集理论设计,堆空间分为:

逻辑上分为:新生区+养老区+元空间(方法区)

实际上的堆(heap)分为:新生区+养老区

新生区具体细分为:

Eden + Survivor1 或 Survivor2 (Survivor1与Survivor2只有一个存放信息)

Eden + from 或 to

各区域的默认比例与设置参数

默认情况下:

新生区 : 养老区 = 1/3:2/3

Eden :S1 :S2 = 8/10:1/10:1/10

堆空间大小的设置

这里实际上指 新生区 + 养老区

-Xms:用于表示堆区的起始内存 (-X:是jvm的运行参数;ms:是memory start)

-Xmx:用于表示堆区的最大内存 (mx:是memory maximum)

查看堆使用率

(一)方法一
# 获取pid
jps
jstat -gc pid

(二)方法二
# 添加参数
-XX:+PrintGCtails

实例分配的过程与回收过程

(1)新对象申请
(2)Eden判断是否放得下
 Eden放得下,将新对象分配到Eden
 Eden放不下,发生一次YGC,YGC后再进行判断Eden是否放得下
 Eden放得下,将新对象分配到Eden
 超大对象,Eden放不下,判断Old是否放得下
 Old放得下,将新对象分配到Old
 Old放不下,发生一次FGC,FGC后再进行判断Old是否放得下
 Old放得下,将对象分配到Old
 Old放不下,发生outofmemory(OOM)

YGC的动作:
(1)YGC时,回收Eden与Servivor中没有对象的实例
 剩余的实例存放到空的S0/S1中,这种情况是S0/S1空间足够
 这个时候会判断对象是否age>阈值(默认15),是则直接放到养老区
 S0/S1空间不足时,将实例放到养老区

FGC的动作:
(1)YGC时,回收Old中没有对象的实例



## 特别需要注意的:
(1)发生GC时,会导致用户线程(作业线程)暂停。
(2)实例每在新生区移动一次,age+1

MinorGC、MajorGC、FullGC的区别

GC按照回收区域分为两大种类型:

(1)部分收集(Partial GC)

(2)整堆收集(Full GC)

新生区GC触发机制与特性

养生区触发机制与特性

特别的:目前,只有CMS收集器会有单独收集老年代的行为。其他收集器均无此行为。



Full GC触发机制与特性

对整堆(新生代,养生代)和方法区的垃圾收集。

触发机制:

总结





JAVA堆分代思想

内存分配策略



TLAB (给每个线程单独分配的缓冲区,私有)

thread local allocation buffer

优势:提高对象的创建效率

为什么有TLAB

什么是TLAB

参数:

# TLAB的开与关
-XX:+UseTLAB
-XX:-UseTLAB

# 设置TLAB空间所占用Eden空间的百分比大小
-XX:TLABWasteTargetPercent=1

堆空间的参数设置

-Xms10m
设置堆最小值为10M

-Xmx10m
设置堆最大值为10M

-XX:SurvivorRatio=8
年轻代中Eden区与两个Survivor区的比值。注意Survivor区有两个。如:8,表示Eden:Survivor=8:1,一个Survivor区占整个年轻代的1/10

-XX:NewRatio=3
设置年轻代(EC+S0C+S1C)和年老代(OC)的比值。如:为3,表示年轻代与年老代比值为1:3,年轻代占整个年轻代年老代和的1/4(jdk1.8,默认2)

-XX:+PrintGCDetails
打印GC的具体信息


-XX:loggc:D:/a.log
将jvm的日志存储到指定文件

#参考链接
https://www.jianshu.com/p/bcdae3c80c1d

上一篇下一篇

猜你喜欢

热点阅读