Java从Jdk1.2版本开始将对象分为了四种状态,目的是为了更好的灵活管理对象的生命周期,分别是强引用,弱引用,软引用,虚引用。
强引用
当对象与强引用关联时,JVM宁愿抛出outofMemory也不会将该对象回收。以下示例即为强引用
String s="test"
弱引用
当对象与弱引用关联时,Jvm进行垃圾回收的时候,会将该对象回收,不管内存是否足够,都将回收。
场景:我们往handler中传入上下文时,对该上下文进行软引用关联,可以节省出内存空间,避免oom
String test = "test";
WeakReference<String> s=new WeakReference<String>(test);
System.out.println(s.get());
System.gc();
System.out.println(s.get());
输出:
test
null
软引用
&emsp;当对象与软引用关联时,JVM会在内存不足的时候将对象回收
场景:缓存-将对象进行软引用关联,然后放入缓存中,当内存不足时会将缓存清理掉,如果没有清理,那就直接用,清理掉了,就重新创建
String test = "test";
SoftReference<String> s=new SoftReference<String>(test);
场景示例:
public class FileData {
private SoftReference<byte[]> data;
public FileData () {
data= new SoftReference<byte[]>(new byte[0]);
}
private byte[] readFileInput() {
return new byte[1024];
}
public byte[] getCache() {
byte[] databyte = data.get();
if (databyte == null || databyte .length == 0) {
databyte = readFileInput();
data = new SoftReference<byte[]>(databyte );
}
return databyte ;
}
}
虚引用
虚引用也是在垃圾回收器回收垃圾的时候会直接被回收掉,就算内存足够也会被回收,和弱引用一样,但是虚引用在要回收的时候并且在回收之前就会被放入ReferenceQueue中,我们可以通过检查这个队列中是否有值来判断该虚引用是否是要被回收了(其他引用都是在回收后放入ReferenceQueue的,虚引用在要回收的时候,并且在回收前)
String test = "test";
PhantomReference<String> phantomReference = new PhantomReference<>(test, new ReferenceQueue<String>());