JVM 垃圾收集对不同类型的引用的有一种不同的方法。java对于它的对象。仅仅存在有引。它会一直存在于内存中。假设越来越多这样的对象,外JVM的内存量。JVM抛出OutOfMemory错。
虽然垃圾收集的实施细节JVM控制。发者仍然能够在一定程度上与垃圾回收器进行交互,其目的在于更好的帮助垃圾回收器管理好应用的内存。这种交互方式就是使用JDK1.2 引入的 java.lang.ref包。
强引用(strong reference)
在一般的 Java 程序中,见到最多的就是强引用(strong reference)。如 Date date = newDate(),date 就是一个对象的强引用。
对象的强引用能够在程序中到处传递。非常多情况下,会同一时候有多个引用指向同一个对象。强引用的存在限制了对象在内存中的存活时间。
假如对象 A 中包括了一个对象 B 的强引用。那么普通情况下,对象 B 的存活时间就不会短于对象 A。
假设对象 A 没有显式的把对象 B 的引用设为 null 的话,就仅仅有当对象 A 被垃圾回收之后。对象 B 才不再有引用指向它。才可能获得被垃圾回收的机会。
软引用(soft reference)
软引用(soft reference)在强度上弱于强引用,通过类SoftReference来表示。
它的作用是告诉垃圾回收器。程序中的哪些对象是不那么重要。当内存不足的时候是能够被临时回收的。当JVM中的内存不足的时候,垃圾回收器会释放那 些仅仅被软引用所指向的对象。假设所有释放完这些对象之后,内存还不足,才会抛出OutOfMemory错误。软引用很适合于创建缓存。当系统内存不足的时候,缓存中的内容是能够被释放的。比方考虑一个图像编辑器的程序。该程序会把图像文件的所有内容都读取到内存中。以方便进行处理。而用户也能够同一时候打开 多个文件。当同一时候打开的文件过多的时候,就可能造成内存不足。假设使用软引用来指向图像文件内容的话,垃圾回收器就能够在必要的时候回收掉这些内存。
import java.lang.ref.SoftReference; public class ImageData { private String path; private SoftReference<byte[]> dataRef; public ImageData(String path) { this.path = path; dataRef = new SoftReference<byte[]>(new byte[0]); } private byte[] readImage() { return new byte[1024 * 1024]; // 省去了读取文件的操作 } public byte[] getData() { byte[] dataArray = dataRef.get(); if (dataArray == null || dataArray.length == 0) { dataArray = readImage(); dataRef = new SoftReference<byte[]>(dataArray); } return dataArray; } } |
在执行上面程序的时候,能够使用 -Xmx 參数来限制JVM可用的内存。因为软引用所指向的对象可能被回收掉。在通过 get方法来获取软引用所实际指向的对象的时候,总是要检查该对象是否还存活。