📜  Java的.lang.ref.SoftReference类在Java中(1)

📅  最后修改于: 2023-12-03 15:32:04.411000             🧑  作者: Mango

Java的.lang.ref.SoftReference类在Java中

简介

在 Java 中,java.lang.ref.SoftReference 类表示对一个柔性引用的对象,即该对象只有在内存不足时才会被回收。这种对象被称为柔性引用(Soft Reference),它可以通过调用 .get() 方法来获得引用的对象,或通过调用.clear() 方法来清除引用。当内存不足时,JVM 将会自动回收该对象,以释放内存。

为什么要使用 SoftReference?

Java 中的垃圾回收器负责回收不再使用的对象,但是垃圾回收是一个相对昂贵的操作,因此在 Java 程序中,不应该滥用垃圾回收。

当一个对象不再被程序所引用,它进入了可回收状态,稍后将被回收掉。如果该对象是资源密集型的对象,如图像、音频、 I/O 缓冲区等,因为这类对象占用很大的内存,垃圾回收机制将无法及时回收这些对象,从而导致内存泄漏和 OutOfMemoryError。

使用柔性引用可以防止内存泄漏,提高 JVM 垃圾回收的效率。使用柔性引用的对象在 GC 时有可能被回收,但是只会在内存不足时才会被回收。这样,一旦内存不足时,JVM 就可以优先回收柔性引用的对象,从而保证程序的正常运行。

例子
import java.lang.ref.SoftReference;

public class Main {
    public static void main(String[] args) throws InterruptedException {
        SoftReference<byte[]> softRef = new SoftReference<>(new byte[1024 * 1024 * 50]); // 50 MB 的柔性引用
        System.out.println("分配了50M的内存");
        System.out.println("软引用的状态:" + softRef.get());

        System.gc(); // 强制垃圾回收

        System.out.println("调用 System.gc() 方法后,软引用的状态:" + softRef.get());

        byte[] bytes = new byte[1024 * 1024 * 50]; // 分配 50 MB 的内存
        System.out.println("再次分配50M的内存");
        System.out.println("软引用的状态:" + softRef.get());
    }
}

输出结果:

分配了50M的内存
软引用的状态:[B@266474c2
调用 System.gc() 方法后,软引用的状态:[B@266474c2
再次分配50M的内存
软引用的状态:null

从上述程序的输出结果中可以看出,当内存充足时,柔性引用所引用的对象并不被回收,而是一直存在于内存中。只有当我们尝试分配其他 50MB 的内存时,由于内存不足,JVM 自动回收了垃圾,柔性引用指向的对象被回收。

总结

使用柔性引用可以防止程序中内存泄漏,并在内存不足时帮助 JVM 有效地清理内存。但是,使用柔性引用时需要注意,因为 JVM 不保证柔性引用超过其初始大小存活多长时间。因此,程序员需要根据实际情况来选择适当的柔性引用大小,以确保程序的稳定运行。