强引用 StrongReference
软引用 SoftReference
弱引用 WeakReference
虚引用 PlantomReference
本文章首发于微信公众号(biglead) 我的大前端生涯 ,同步刊登各技术论坛。
对于强引用,我们平时在编写代码时经常会用到。而对于其他三种类型的引用,使用得最多的就是软引用和弱引用,这2种既有相似之处又有区别。它们都是用来描述非必需对象的,但是被软引用关联的对象只有在内存不足时才会被回收,而被弱引用关联的对象在JVM进行垃圾回收时总会被回收。
在使用软引用和弱引用的时候,我们可以显示地通过System.gc()来通知JVM进行垃圾回收,但是要注意的是,虽然发出了通知,JVM不一定会立刻执行,也就是说这句是无法确保此时JVM一定会进行垃圾回收的。
1 强引用在java中,new一个Object(对象)存放在堆内存,然后用一个引用指向它,这就是强引用。
如果一个对象具有强引用,那垃圾回收器绝不会回收它。
当内存空间不足,Java虚拟机宁愿抛出OutOfMemoryError错误,使程序异常终止,也不会靠随意回收具有强引用的对象来解决内存不足的问题
2 软引用
如果一个对象只具有软引用,则内存空间足够时,垃圾回收器就不会回收它;如果内存空间不足了,就会回收这些对象的内存
也就是内存溢出之前进行回收
2.1 代码使用方法
//创建对象(obj 此时的引用为强引用)
Object obj = new Object();
//构建关联软引用
SoftReference sf = new SoftReference(obj);
//释放强引用
obj = null;
//获取刚刚创建的对象
//get方法用来获取与软引用关联的对象的引用,如果该对象被回收了,则返回null
sf.get();//有时候会返回null
//这时候sf是对obj的一个软引用,通过sf.get()方法可以取到这个对象,当然,当这个对象被标记为需要回收的对象时,则返回null;
3 弱引用
弱引用与软引用的区别在于:只具有弱引用的对象拥有更短暂的生命周期
也就是第二次垃圾回收时回收
每次执行GC的时候,一旦发现了只具有弱引用的对象,不管当前内存空间足够与否,都会回收它的内存。不过,由于垃圾回收器是一个优先级很低的线程,因此不一定会很快发现那些只具有弱引用的对象
3.1 代码使用方法
//创建对象
Object obj = new Object();
//构建关联弱引用
WeakReference wf = new WeakReference(obj);
//释放强引用
obj = null;
//有时候会返回null
//弱引用是在第二次垃圾回收时回收,短时间内通过弱引用取对应的数据,可以取到,当执行过第二次垃圾回收时,将返回null。
wf.get();
//返回是否被垃圾回收器标记为即将回收的垃圾
//弱引用主要用于监控对象是否已经被垃圾回收器标记为即将回收的垃圾,可以通过弱引用的isEnQueued方法返回对象是否被垃圾回收器标记。
wf.isEnQueued();
4 虚引用
垃圾回收时回收,无法通过引用取到对象值
形同虚设,与其他几种引用都不同,虚引用并不会决定对象的生命周期。如果一个对象仅持有虚引用,那么它就和没有任何引用一样,在任何时候都可能被垃圾回收器回收
//创建对象
Object obj = new Object();
//构建关联虚引用
PhantomReference pf = new PhantomReference(obj);
//释放强引用
obj=null;
//永远返回null
//虚引用是每次垃圾回收的时候都会被回收,通过虚引用的get方法永远获取到的数据为null,因此也被成为幽灵引用。
pf.get();
//返回是否从内存中已经删除
//虚引用主要用于检测对象是否已经从内存中删除
pf.isEnQueued();