187_java中的引用类型
2016-06-05 23:47
281 查看
java中的引用类型
java中对象的引用分为4类
级别从高到低依次是
1.强引用
2.软引用
3.弱引用
4.虚引用
强引用
我们平时用的都是强引用,
垃圾回收器是绝对不会回收强引用的,
当内存不足的时候,java虚拟机就算抛出OOM异常,也不回收强引用的对象
java的对象是放在堆内存(heap)中的,堆内存中有强可及对象、软可及对象、弱可及对象、虚可及对象和不可到
达对象,
举例来说明一下
String abc=new String("abc"); //1
SoftReference<String> softRef=new SoftReference<String>(abc); //2
WeakReference<String> weakRef = new WeakReference<String>(abc); //3
abc=null; //4
softRef.clear();//5
第一行在 heap 堆中创建内容为“abc”的对象,并建立
abc 到该对象的强引用,该对象是强可及的。
第二行和第三行分别建立对 heap 中对象的软引用和弱引用,此时
heap 中的
abc 对象已经有
3 个引用,显然此
时 abc 对象仍是强可及的。
第四行之后 heap 中对象不再是强可及的,变成软可及的。
第五行执行之后变成弱可及的。
软引用
如果一个对象只有软引用,
内存够的时候,不会回收
但是内存不够的时候,就会回收
软引用可以用来实现内存敏感的高速缓存
软引用可以和一个引用队列(ReferenceQueue)联合使用
如果软引用对象被回收Java虚拟机会把这个软引用加入到和他关联的引用队列里
软引用主要用于内存敏感的高速缓存
jvm报告内存不足之前,会清除所有的软引用这样gc就有可能回收软可及的对象,解决内存不足问题,避免内存溢出
什么时候被回收取决于gc的算法和gc运行时可用内存的大小
当gc决定要回收软引用的时候执行以下过程,比如刚刚的softRef
1 首先将 softRef的 referent(abc)设置为
null,不再引用
heap 中的
new String("abc")对象。
2 将 heap
中的 new String("abc")对象设置为可结束的(finalizable)。
3 当 heap
中的 new String("abc")对象的
finalize()方法被运行而且该对象占用的内存被释放,softRef
被添加到它的 ReferenceQueue(如果有的话)中。
注意:对
ReferenceQueue 软引用和弱引用可以有可无,但是虚引用必须有。
被 Soft Reference 指到的对象,即使没有任何
Direct Reference,也不会被清除。一直要到
JVM 内存
不足且没有 Direct Reference 时才会清除,SoftReference
是用来设计 object-cache
之用的。如此一来
SoftReference 不但可以把对象 cache
起来,也不会造成内存不足的错误
弱引用
如果一个对象只有弱引用,那么他就是可有可无的对象
因为gc随时会干掉他
弱引用和软引用的区别在于: 弱引用不管内存大小,直接回收
不过gc是一个优先级很低的线程,所以不一定会很快发现这些只有弱引用的对象
弱引用可以和一个引用队列(ReferenceQueue)联合使用,如果弱引用所引用的对象被垃圾回收,Java
虚
拟机就会把这个弱引用加入到与之关联的引用队列中
虚引用
虚引用随时都可能被回收,就和没有任何引用一样
虚引用与软引用和弱引用的一个区别在于:虚引用必须和引用队列(ReferenceQueue)联合使用。当垃圾
回收器准备回收一个对象时,如果发现它还有虚引用,就会在回收对象的内存之前,把这个虚引用加入到与之关
联的引用队列中。程序可以通过判断引用队列中是否已经加入了虚引用,来了解被引用的对象是否将要被垃圾回
收。程序如果发现某个虚引用已经被加入到引用队列,那么就可以在所引用的对象的内存被回收之前采取必要的
行动。
建立虚引用之后通过 get 方法返回结果始终为
null,通过源代码你会发现,虚引用通向会把引用的对象写进
referent,只是 get
方法返回结果为 null。先看一下和
gc 交互的过程再说一下他的作用。
1 不把 referent
设置为 null,
直接把 heap
中的 new String("abc")对象设置为可结束的(finalizable)。
2 与软引用和弱引用不同,
先把 PhantomRefrence
对象添加到它的 ReferenceQueue
中.然后在释放虚可
及的对象。
相关文章推荐
- [原创]java WEB学习笔记42:带标签体的自定义标签,带父标签的自定义标签,el中自定义函数,自定义标签的小结
- JavaAPI之注释类型Retention
- java多线程编程之Callable、Future和FutureTask。
- Java并行编程-lock中使用多条件condition(生产者消费者模式实例)
- java.util.Map源码分析
- Java 帝国之Java bean(下)
- Spring MVC 遇到的一点点问题(转)
- KMP,父串匹配子串算法,java实现
- JavaAPI之ElementType枚举类
- Java Sax解析xml
- 堆排序
- Set、List、Map的总结
- 优先队列
- java基础-filter
- JavaAPI之注释类型Target
- [置顶] 初探JVM的背面JPDA(Java Platform Debugger Architecture)
- Hadoop学习笔记(二)——插件安装和使用(Hadoop Eclipse)
- Java基础之String类型的使用
- 第一个Java web项目
- 分布式锁1 Java常用技术方案