20210812GC以及JVM的GC第一篇
编辑时间:2021/08/12
读完本节:大概花费6分钟,共895词
文章目录
1.内存模型
1.栈帧 堆
2.垃圾回收是针对堆区的内存空间
3.对堆区内存空间的操作可能会产生两个问题
3.1memory leak 内存泄漏
-
多个指针或引用指向同一块内存空间时,其中某一个指针或引用释放了该空间,导致其他指向这块内存空间的指针或引用有泄漏的风险,即表示这块空间有可能会被其他无关当前栈帧的指针或引用访问和操作。
-
当堆空间的垃圾回收慢或者不回收时会产生memory run out问题
3.2野指针问题
-
访问指向不存在的指针或引用
-
多个指针或引用指向同一块内存空间,当它们其中一个被释放回收后,其余指针变为野指针
2.什么是垃圾回收器
1.什么是垃圾
当一个堆空间的一块内存没有继续再引用且没有继续指向堆空间中其他位置时,可以将这块空间所存储得内容视为垃圾
2.如何标记垃圾
2.1常用的垃圾标记算法
-
引用计数法
-
原理:
对每个对象保存一个整型的引用计数器属性,用于记录对象被引用的情况。每当有一个引用指向这个对象时,引用计数器自增1;当当前对像减少一个引用指向时,引用计数器自减1;当引用计数器属性值为0时表示,当前对象没有被引用指向
-
pros
- 实现简单,垃圾对象便于辨识,判定回收高效,回收不具有延迟性;
-
cons
- 需要额外的空间(字段)存储计数器,这样增加了存储空间的开销
- 每次赋值(引用指向或者取消引用指向),需要对计数器的值进行修改,增加了时间开销
- 最严重的问题是:引用计数法无法解决已经处于循环引用的垃圾,即若干个对象JVM不在使用,但是,这几个对象之间相互引用,导致引用计数器的值不为0,因此不能被标记为垃圾回收。
-
-
根可达算法(Java虚拟机使用的策略)
- 原理:首先从GC Root对象作为树的根节点,然后在树中向叶子结点遍历,得到搜索走过的路径(引用链)。当一个对象不处于引用链之上时,可以认为这个对象是垃圾
- pros
- 解决了无法回收循环引用的问题,减少程序运行过程中循环引用对内存空间的占用
- cons
- 对于引用层级很深的对象,需要花费较大的时间去搜索
- 对象被回收的时间不能确定,由JVM决定
- GC Root的常见对象有:
- 虚拟机线程(thread)中,虚拟机栈(virtual machine stack)中本地变量表(frame)引用的对象
- 位于方法区(method area)中静态属性引用,常量引用duixang
- 本地方法栈中(native method stack)JNI引用的对象
2.2图解两种算法
-
引用计数法
-
根可达算法