1, 利用软引用和弱引用解决 OOM 问题: 用一个 HashMap 来保存图片的路径和相应图片对象关联的软引用之间的映射关系, 在内存不足时, JVM 会自动回收这些缓存图片对象所占用的空间, 从而有效地避免了 OOM 的问题;
2, 通过软引用对象重获方法实现 java 对象的高速缓存: 比如我们创建了一个 Employee 类, 如果每次需要查询一个雇员的信息. 哪怕是几秒钟之前刚刚查询过的, 都要重新构建一个实例, 这是需要消耗很多时间的. 我们可以通过软引用和 HashMap 的结合, 先是保存引用方面: 以软引用的方式对一个 Employee 对象的实例进行引用并保存该引用到 HashMap 上, key 为此雇员的 id,value 为这个对象的软引用, 另一方面是取出引用, 缓存中是否有该 Employee 实例的软引用, 如果有, 从软引用中取得 . 如果没有软引用, 或者从软引用中得到的实例是 null, 重新构建一个实例, 并保存对这个新建实例的软引用;
3, 强引用: 如果一个对象具有强引用, 它就不会被垃圾回收器回收. 即使当前内存空间不足, JVM 也不会回收它, 而是抛出 OutOfMemoryError 错误, 使程序异常终止. 如果想中断强引用和某个对象之间的关联, 可以显示的将引用赋值为 null, 这样一来的话, JVM 在合适的时间就会回收对象;
4, 弱引用: 具有弱引用的对象拥有的生命周期更短暂. 因为当 JVM 进行垃圾回收, 一旦发现弱引用对象, 无论当前内存空间是否充足, 都会将弱引用回收. 不过由于垃圾回收器是一个优先级较低的线程, 所以并不一定能迅速发现弱引用对象;
5, 虚引用: 顾名思义, 就是形同虚设, 如果一个对象仅持有虚引用, 那么它相当于没有引用, 在任何时候都有可能被垃圾回收器回收.
- public static void soft() throws Exception {
- Object obj = new Object();
- ReferenceQueue rq = new ReferenceQueue < >();
- SoftReference sr = new SoftReference(obj, rq); // 创建关于 obj 的软引用, 使用引用队列
- System.out.println(sr.get()); //get 方法会输出这个 obj 对象的 hashcode
- System.out.println(rq.poll()); // 输出为 null
- obj = null;
- System.gc();
- Thread.sleep(200); // 因为 finalizer 线程优先级很低, 所以让线程等待 200ms
- System.out.println(sr.get()); // 因为堆空间没满, 可有可无的特性, 所以还是会输出这个 obj 对象的 hashcode
- System.out.println(rq.poll()); // 自然队列为 null
- }
- public static void weak() throws Exception {
- Object obj = new Object();
- ReferenceQueue rq = new ReferenceQueue < >();
- WeakReference wr = new WeakReference(obj, rq);
- System.out.println(wr.get());
- System.out.println(rq.poll());
- obj = null;
- System.gc();
- Thread.sleep(200);
- System.out.println(wr.get()); // 这时候会输出 null
- System.out.println(rq.poll()); //rq 队列里也会存放这个弱引用, 输出它的 hashcode
- }
来源: http://www.bubuko.com/infodetail-2770943.html