JAVA基础:强引用、软引用、弱引用、虚引用

生活

任何傻瓜都能写出计算机可以理解的代码。好的程序员能写出人能读懂的代码。

前言

在JAVA中,开发人员不需要像C开发人员那样手动去管理内存中对象的生命周期,但是如果需要某些对象具备一定的生命周期(当内存不足的时候可以回收一些没有必要的对象,从而规避一些OOM的风险),此时可以通过弱引用和软引用、虚引用来实现生命周期的管理。

强引用

注意:JAVA中写的大部分代码都是强引用。
当一个对象被一个强引用关联时,JVM必定不会回收这个对象,就算内存不足了,宁可出现OOM也不回收。
例如这段代码:

public static void  test() {
		Object[] object = new Object[10000];
	}

在分配内存给数组时,即使出现内存不足,也不会回收。
注意在这个方法执行完毕后,object这个强引用也就不存在了,那数组对象就能被jvm回收了。

软引用

软引用用来描述一些有用但又没那么必须的对象,,在Java中用java.lang.ref.SoftReference类来表示。被软引用关联的对象在内存不足时就会被JVM回收,这一点可以很好的用在oom的场景上,并且这个特性适合用在缓存上:比如网页缓存、图片缓存。
软引用可以与一个引用队列关联使用,当一个软引用所引用的对象被JVM回收,这个软引用就会被加入到与之关联的引用队列上。
代码如下:

SoftReference<String> s = new SoftReference<String>(new String("a"));
		System.out.println(s.get());

弱引用

弱引用用来描述一些非必须对象,它的优先级比软引用还要低,在JAVA中用java.lang.ref.WeakRefrence来表示。
被弱引用关联的对象,在JVM进行垃圾回收时,无论内存是否充足,都会回收。
同样,弱引用也可以与一个引用队列关联使用,当一个弱引用所描述的对象被JVM回收,这个弱引用就会被加入与之关联的引用队列上。

ReferenceQueue<String> q = new ReferenceQueue<>();
		WeakReference<String> s = new WeakReference<String>(new String("a"),q);
		
		System.out.println(s.get());
		System.out.println(q.poll());
		System.gc();
		System.out.println(s.get());
		System.out.println(q.poll());

结果:
a
null
null
java.lang.ref.WeakReference@15db9742

虚引用

虚引用跟前面的弱引用、软引用不一样,它不影响对象的生命周期,被他所表示的对象可以随时被垃圾回收器回收。
在java中用java.lang.ref.PhantomReference类表示一个虚引用。
虚引用必须与引用队列关联使用,当JVM准备回收一个对象时,如果发现它存在虚引用,会先把它放到它关联的引用队列,程序可以通过引用队列里是否有相关的虚引用,来判断对象是否即将被回收。
如果发现某个虚引用出现在引用队列里,既可以在这个引用所引用的对象的内存空间被回收之前做出一些必要的操作。

 ReferenceQueue<String> queue = new ReferenceQueue<String>();
	        PhantomReference<String> pr = new PhantomReference<String>(new String("hello"), queue);
	        System.out.println(pr.get());

null
注意虚引用的GET取到的对象只有null。

虚引用的一个使用:DirectByteBuffer

如何利用软引用和弱引用解决OOM问题

前面讲了关于软引用和弱引用相关的基础知识,那么到底如何利用它们来优化程序性能,从而避免OOM的问题呢?

下面举个例子,假如有一个应用需要读取大量的本地图片,如果每次读取图片都从硬盘读取,则会严重影响性能,但是如果全部加载到内存当中,又有可能造成内存溢出,此时使用软引用可以解决这个问题。

设计思路是:用一个HashMap来保存图片的路径 和 相应图片对象关联的软引用之间的映射关系,在内存不足时,JVM会自动回收这些缓存图片对象所占用的空间,从而有效地避免了OOM的问题。在Android开发中对于大量图片下载会经常用到。

猜你喜欢

转载自blog.csdn.net/qq_28605513/article/details/84872974