引用类背后的目的就是避免在应用程序执行期间将对象留在内存中。
您以软引用,弱引用,虚引用的方式引用对象,垃圾收集器就能够随意地释放对象。
当您希望尽可能减小引用程序在其生命周期中使用的堆内存大小时,这种用途就很有好处。
必须记住的是,要使用这些类,就不能保留对对象的强引用。如果您确实保留了对象的强引用,那么就会浪费这些引用类提供的好处。
您还必须使用正确的编程风格在使用对象之前检查垃圾收集器是否已经回收了它,如果已经回收了,您首先必须考虑重新创建该对象。这个过程可以用不同的编程风格来完成。选择错误的风格会导致出问题滴。
[code]import java.io.FileNotFoundException;
import java.io.FileReader;
import java.lang.ref.WeakReference;
public class ReferenceIdiom {
public static void main(String args[]) throws FileNotFoundException, InterruptedException{
broken();
correct();
}
public static FileReader recreateIt() throws FileNotFoundException {
return new FileReader("F:/lomboz/eclipse/workspace/temp.fil");
}
/**
* 一个错误的示范
* @throws FileNotFoundException
* @throws InterruptedException
*/
public static void broken() throws FileNotFoundException, InterruptedException {
System.out.println("Executing mehtod broken");
FileReader obj = recreateIt();
WeakReference wr = new WeakReference(obj);
System.out.println("wr refers to object" + wr.get());
System.out.println("Now, clear the reference and run GC");
//清理强引用,运行GC以回收obj所引用的对象
obj = null;
System.gc();
Thread.sleep(1500); //给垃圾回收线程让出足够的CPU时间
System.out.println("wr refers to object " + wr.get());
//如果对象已经被回收,则重新创建它
obj = (FileReader)wr.get();
if (obj == null) {
System.out.println("Now, recreate the object and wrap it in a WeakReference");
wr = new WeakReference(recreateIt());//这样创建的FileReader对象是没有强引用的
System.gc();
Thread.sleep(1500);
obj = (FileReader)wr.get(); //这里由99.99%的可能为空
}
System.out.println("wr refers to object " + wr.get());
}
public static void correct() throws FileNotFoundException, InterruptedException {
System.out.println("");
System.out.println("Executing method correct");
FileReader obj = recreateIt();
WeakReference wr = new WeakReference(obj);
System.out.println("wr refers to object " + wr.get());
System.out.println("Now, clear the reference and run GC");
obj = null;
System.gc();
Thread.sleep(1500);
System.out.println("wr refers to object " + wr.get());
//Now see if obj was collected and recreate it if it was.
obj = (FileReader)wr.get();
if (obj == null) {
System.out.println("Now, recreate the object and wrap it in a WeakReference");
obj = recreateIt();
wr = new WeakReference(obj);
System.gc();
Thread.sleep(1500); // FileReader is pinned, this will not affect anything.
}
System.out.println("wr refers to object " + wr.get());
obj = null; //用完了记得清理
}
}[/code]
您以软引用,弱引用,虚引用的方式引用对象,垃圾收集器就能够随意地释放对象。
当您希望尽可能减小引用程序在其生命周期中使用的堆内存大小时,这种用途就很有好处。
必须记住的是,要使用这些类,就不能保留对对象的强引用。如果您确实保留了对象的强引用,那么就会浪费这些引用类提供的好处。
您还必须使用正确的编程风格在使用对象之前检查垃圾收集器是否已经回收了它,如果已经回收了,您首先必须考虑重新创建该对象。这个过程可以用不同的编程风格来完成。选择错误的风格会导致出问题滴。
[code]import java.io.FileNotFoundException;
import java.io.FileReader;
import java.lang.ref.WeakReference;
public class ReferenceIdiom {
public static void main(String args[]) throws FileNotFoundException, InterruptedException{
broken();
correct();
}
public static FileReader recreateIt() throws FileNotFoundException {
return new FileReader("F:/lomboz/eclipse/workspace/temp.fil");
}
/**
* 一个错误的示范
* @throws FileNotFoundException
* @throws InterruptedException
*/
public static void broken() throws FileNotFoundException, InterruptedException {
System.out.println("Executing mehtod broken");
FileReader obj = recreateIt();
WeakReference wr = new WeakReference(obj);
System.out.println("wr refers to object" + wr.get());
System.out.println("Now, clear the reference and run GC");
//清理强引用,运行GC以回收obj所引用的对象
obj = null;
System.gc();
Thread.sleep(1500); //给垃圾回收线程让出足够的CPU时间
System.out.println("wr refers to object " + wr.get());
//如果对象已经被回收,则重新创建它
obj = (FileReader)wr.get();
if (obj == null) {
System.out.println("Now, recreate the object and wrap it in a WeakReference");
wr = new WeakReference(recreateIt());//这样创建的FileReader对象是没有强引用的
System.gc();
Thread.sleep(1500);
obj = (FileReader)wr.get(); //这里由99.99%的可能为空
}
System.out.println("wr refers to object " + wr.get());
}
public static void correct() throws FileNotFoundException, InterruptedException {
System.out.println("");
System.out.println("Executing method correct");
FileReader obj = recreateIt();
WeakReference wr = new WeakReference(obj);
System.out.println("wr refers to object " + wr.get());
System.out.println("Now, clear the reference and run GC");
obj = null;
System.gc();
Thread.sleep(1500);
System.out.println("wr refers to object " + wr.get());
//Now see if obj was collected and recreate it if it was.
obj = (FileReader)wr.get();
if (obj == null) {
System.out.println("Now, recreate the object and wrap it in a WeakReference");
obj = recreateIt();
wr = new WeakReference(obj);
System.gc();
Thread.sleep(1500); // FileReader is pinned, this will not affect anything.
}
System.out.println("wr refers to object " + wr.get());
obj = null; //用完了记得清理
}
}[/code]