Java:使用弱引用进行堆栈



在Java中,有一种称为WeakHashMap的数据结构,它将弱引用存储为键。 每当从内存中删除弱引用时,该条目都会从映射中删除。

如果我有一个数据结构,如堆栈或集合,我在其中存储弱引用,当弱引用从内存中取出时,它们的条目会自动删除吗?

下面是一个存储弱引用的堆栈示例。

Stack<WeakReference<Object>> objStack = new Stack<WeakReference<Object>>();

是的。你所描述的是一般的弱引用的属性,而不是具体的WeakHashMap

从 API :

假设垃圾回收器在某个时间点确定对象是弱可访问的。届时,它将以原子方式清除对该对象的所有弱引用......

迟到总比没有好。

这不是弱引用的工作方式。WeakReference -object 将始终存在,但其get() -方法可能会返回原始对象或null(如果原始对象是 GC:ed)。

这意味着您的堆栈将始终包含一个WeakReference对象。

这是我做的一个详细的测试(但是这取决于 JVM 在中间执行 GC,这可能会也可能不会"根据命令"发生 - 如果没有发生,请尝试添加更多System.gc() :s):

public static void main(String[] args) {
    // Set up
    Object object = new Object();
    final WeakReference<Object> weakReference = new WeakReference<>(object);
    final Stack<WeakReference<Object>> references = new Stack<>();      
    references.add(weakReference);
    // Before
    System.out.println("Before:");
    references.forEach(r -> {
        System.out.println("Reference: " + r);
        System.out.println("Object: " + r.get());
    });
    // GC
    object = null;
    System.gc();
    System.gc();
    System.gc();
    // After
    System.out.println("After:");
    references.forEach(r -> {
        System.out.println("Reference: " + r);
        System.out.println("Object: " + r.get());
    });
}

输出:

Before:
Reference: java.lang.ref.WeakReference@238e0d81
Object: java.lang.Object@31221be2
After:
Reference: java.lang.ref.WeakReference@238e0d81
Object: null

最好的方法可能是忽略get()在"弹出"它们后返回null条目。

旁注:我的第一个测试是使用字符串对象,它从未得到GC:ed。这是因为Java中的字符串是"暂留的"(见String.intern()),这意味着有一个隐藏的静态字符串缓存被重用。一个字符串永远不会是GC:ed,除非该字符串池已满(或沿着该行的内容......我认为字符串是唯一具有这种"特殊"特征的 Java 对象,但我建议始终在 WeakReference 中使用自定义对象以确保它正确获得 GC:ed。

相关内容

  • 没有找到相关文章

最新更新