Java引用类型分析

在Java中有几种不同强度的引用类型包括:强引用,软引用,弱引用,终结方法引用,虚引用。因为引用类型的实现和垃圾回收密切相关,所以很多工作都需要在vm中完成。下面将分析这些引用。

1、强引用(StrongReference):普通的引用,回收器永远不会将强引用置空。被StrongReference引用的对象,在GC标记过程中属于(强)可达对象。

2、软引用(SoftReference):回收器会根据内存的情况来判断是否将软引用置空。如果目标对象没有比软引用更强的引用时,那么目标对象属于软可达,下面的可达状态类似。

3、弱引用(WeakReference):回收器发现弱引用的目标对象是弱可达,会立即将引用置空。

4、终结方法引用(FinalReference):目标对象实现了finalize()方法,jvm会为其生成一个终结方法引用,用来实现终结操作。

5、虚引用(PhantomReference):虚引用是强度最弱的引用,不能从该引用获得目标对象,用户程序只能调用引用的clear()方法置空引用。

下面先从JVM的角度来分析引用,以复制算法为例描述回收器对不同引用的处理,回收器遍历进行对象追踪的步骤如下:

1、从GGRoot开始,仅对强引用进行追踪(复制对象本身以及通过该对象可达的对象),同时找出所有软引用、弱引用、终结方法引用以及虚引用(不对这些对象中的弱引用进行追踪,派生类引入的强引用仍然会被追踪)。

2、处理软引用,如果有必要,则将软引用置空,将引用加入pending链表。否则,对软引用进行追踪。

3、处理弱引用,如果弱引用已经复制到目标空间,则更新引用,否则置空引用,将引用加入pending链表。

4、处理终结方法引用,如果引用的目标对象没有被复制到目标空间,则将引用加入pending链表(终结方法执行之后置空引用),并且对目标对象进行追踪。

5、处理虚引用,目标未被复制到目标空间,则目标对象进行追踪,将引用加入pending链表。jvm不会将虚引用置空,置空操作由程序员调用。

上面的流程是VM对引用的处理,可以注意下将引用加入pending链表这个操作。在之前分析Reference源码时已经知道Reference中有两个链表discovery链表和pending链表,这两个链表由jvm进行维护。通过上面的流程可以发现一下几个问题:

1、pending链表,在之前分析Reference源码时已经知道Reference中有两个链表discovery链表和pending链表,这两个链表由jvm进行维护,会有一个线程专门处理pending链表,并将其中的引用加入到对应的ReferenceQueue。

2、当引用被加入pending链表时,软引用的目标对象处于软可达状态,弱引用对象处于弱可达状态,终结方法引用和虚引用也类似。

3、在引用加入pending链表时只有软引用和弱引用的引用被置空了。

4、因为FinalReference的处理在虚引用处理前面,所以虚引用在加入pending链表时,其finalize()方法已经被执行了

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值