java - 弱 HashMap 如何知道对对象进行垃圾回收?

标签 java data-structures garbage-collection weakhashmap

我最近发现了 WeakHashMap Java 中的数据结构。

但是,我不明白它在不再正常使用时对映射进行垃圾收集是什么意思。数据结构如何知道我将不再在我的程序中使用 key ?如果长时间不引用 key 怎么办?

最佳答案

However, I don't understand what it means by it garbage-collects a mapping when it is no longer in ordinary use.

好的。一般情况下,当垃圾收集器运行时,它会移除你的程序不能再使用的对象。技术术语是“无法访问的对象”,它意味着程序执行无法再获得对该对象的引用。一个无法访问的对象,可能会在下一个 GC 周期中被收集……也可能不会。无论哪种方式,它都不再是应用程序的关注点。

在这种情况下,WeakHashMap 使用一个名为WeakReference 的特殊类来引用键1。弱引用是一个对象,其行为有点像间接指针(指向持有指针的对象的指针)。它有一个有趣的特性,即允许垃圾收集器破坏引用;即用 null 替换它包含的引用。并且规则是当 GC 注意到对象不再可以通过普通(强)或软引用链访问时,对对象的弱引用被破坏2.

短语“不再正常使用” 的真正意思是关键对象不再是强可达或软可达;即通过一系列强引用和/或软引用。

How does the data structure know I will no longer use a key in my program?

WeakHashmap 不会这样做。相反,是 GC 注意到 key 不是强可达的。

作为其正常遍历的一部分,GC 将查找并标记所有强可达对象。然后它遍历所有 WeakReference 对象并检查是否 他们引用的对象已被标记,如果没有则破坏它们。 (或者类似的东西……我从来没有看过实际的 GC 实现。而且由于它必须处理 SoftReferencePhantomReference 对象,所以它很复杂还有。)

WeakHashmap 唯一涉及的是:

  • 它为键创建并使用 WeakReference 对象,并且
  • 它删除其关键字 WeakReferences 已被 GC 清除的哈希表条目。

What if I don't refer to a key for a long time?

决定弱引用应该被破坏的标准不是基于时间的。

但时间可能会影响 key 是否被删除。例如,一个键可以 1) 不再是强引用,2) 从映射中检索,以及 3) 分配给一个可到达的变量,使其再次被强引用。如果 GC 未在键不可强访问的窗口期间运行,则键及其关联值将保留在映射中。 (这是你想要发生的事情......)


1 - 实现细节:在最近的 Java 版本中,弱引用实际上指的是 map 的内部 Entry 对象,而不是键。这允许更有效地从映射中清除损坏的引用。详情看代码。
2 - 软引用是一种在堆内存不足时允许 GC 中断的引用。

关于java - 弱 HashMap 如何知道对对象进行垃圾回收?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11173814/

相关文章:

python - 为什么在 Python 中列表访问 O(1)?

java - Java 客户端中的 Soap 连接超时但 SOAPUI 中没有

java - 使用 Spring Cloud Stream 的 Azure 服务总线重试策略

c - 将数字数据存储在二进制文件和数据结构中

c# - 是否可以编写代码来造成无法通过终止进程修复的那种损坏?

android - Bitmap、Bitmap.recycle()、WeakReferences 和垃圾回收

python - 在 Python 2.7 中引发异常后未释放对象

java - 以 lambda 作为参数的 BindingAdapter

java - 按主键查找与按唯一列查找有区别吗?

c - 最有效的动态排序方法