http://liujiacai.net/blog/2015/09/27/java-weakhashmap/
Java 中,引用有四种类型,分别为:强(strong)引用、软(soft)引用、弱(weak)引用、虚(phantom,本意为幽灵👻)引用。
强引用
这是最常用的引用类型,在执行下面的语句时,变量 o 即为一个强引用。
Java 中,引用有四种类型,分别为:强(strong)引用、软(soft)引用、弱(weak)引用、虚(phantom,本意为幽灵👻)引用。
强引用
这是最常用的引用类型,在执行下面的语句时,变量 o 即为一个强引用。
强引用指向的对象无论在何时,都不会被GC 清理掉。
一般来说,对于常驻类应用(比如server),随着时间的增加,所占用的内存往往会持续上升,如果程序中全部使用强引用,那么很容易造成内存泄漏,最终导致
Out Of Memory (OOM)
,所以 Java 中提供了除强引用之外的其他三种引用,它们全部位于java.lang.ref
包中,下面一一介绍。java.lang.ref.Reference
java.lang.ref.Reference
为 软(soft)引用、弱(weak)引用、虚(phantom)引用的父类。
|
如果我们在创建一个引用对象时,指定了
ReferenceQueue
,那么当引用对象指向的对象达到合适的状态(根据引用类型不同而不同)时,GC 会把引用对象本身添加到这个队列中,方便我们处理它,因为引用对象指向的对象 GC 会自动清理,但是引用对象本身也是对象(是对象就占用一定资源),所以需要我们自己清理。
|
ss
为软引用,指向abc
这个对象,abc
会在一定时机被 GC 自动清理,但是ss
对象本身的清理工作依赖于queue
,当ss
出现在queue
中时,说明其指向的对象已经无效,可以放心清理ss
了。
不同的引用,添加到
ReferenceQueue
的时机是不一样。
如果创建引用对象是没有指定
ReferenceQueue
,引用对象会怎么样呢?Reference
类内部的四种状态。四种状态
每一时刻,
Reference
对象都处于下面四种状态中。这四种状态用Reference
的成员变量queue
与next
(类似于单链表中的next)来标示。软引用(soft reference)
软引用“保存”对象的能力稍逊于强引用,但是高于弱引用,一般用来实现memory-sensitive caches。
软引用指向的对象会在程序即将触发OOM
时被GC 清理掉,之后,引用对象会被放到ReferenceQueue
中。
弱引用(weak reference)
软引用“保存”对象的能力稍逊于弱引用,但是高于虚引用,一般用来实现canonicalizing mapping,也就是本文要讲的
WeakHashMap
😊。当弱引用指向的对象只能通过弱引用(没有强引用或弱引用)访问时,GC会清理掉该对象,之后,引用对象会被放到ReferenceQueue
中。
虚引用(phantom reference)
虚引用是“保存”对象能力最弱的引用,一般用来实现scheduling pre-mortem cleanup actions in a more flexible way than is possible with the Java finalization mechanism
调用虚引用的get
方法,总会返回null
,与软引用和弱引用不同的是,虚引用被enqueued
时,GC 并不会自动清理虚引用指向的对象,只有当指向该对象的所有虚引用全部被清理(enqueued后)后或其本身不可达时,该对象才会被清理。