了解Java的引用类:SoftReference、WeakReference和PhantomReference

22 浏览
0 Comments

了解Java的引用类:SoftReference、WeakReference和PhantomReference

有人能解释一下三个引用类之间的区别吗(或者提供一个链接来解释)?SoftReference > WeakReference > PhantomReference,但是我应该在什么时候使用它们呢?为什么有 WeakHashMap,但没有 SoftHashMap 或者 PhantomHashMap

如果我使用以下代码...

WeakReference ref = new WeakReference("Hello!");
if (ref != null) {                 // ref can get collected at any time...
    System.gc();                   // Let's assume ref gets collected here.
    System.out.println(ref.get()); // Now what?!
}

...会发生什么?我是否需要在每个语句之前检查 ref 是否为空(这是错误的,但我应该怎么办)?抱歉问题有点多,但我很难理解这些 Reference 类... 谢谢!

admin 更改状态以发布 2023年5月22日
0
0 Comments

一个链接:https://community.oracle.com/blogs/enicholas/2006/05/04/understanding-weak-references

PhantomHashMap 不会很好的工作,因为幽灵引用对应的 get 总是返回 null

缓存很棘手,因此 SoftHashMap 可能不如你想象的那样好。但是,我相信谷歌的集合库包含了一个通用的引用映射实现。

你应该始终检查 get 是否返回非 null。(注意,不要检查 Reference 引用本身是否为非 null。)在字符串内部化的情况下,它总是会的,但(如往常一样)不要试图“聪明地”处理它。

0
0 Comments

Java库文档中的java.lang.ref包的文档描述了三种显式引用类型的弱化强度。

当您希望引用的对象在主机进程的内存不足时仍然保持活动状态时,可以使用SoftReference。该对象直到收集器需要释放内存之前才能被回收。粗略地说,绑定SoftReference的含义是“把对象固定住,直到不能再固定为止”。

相反,当您不希望影响引用对象的生命周期时,可以使用WeakReference。您仅希望对引用对象做出单独的断言,只要引用对象存活即可。存在绑定的WeakReference不会影响对象被收集的资格。例如将对象实例映射到相关属性的外部映射,只要相关对象存活,就需要记录属性,这是使用WeakReferenceWeakHashMap的好方法。

最后一个-PhantomReference-更难以描述。像WeakReference一样,这样绑定的PhantomReference对引用对象的生命周期没有影响。但是,与其他引用类型不同,甚至连PhantomReference都无法取消引用。在某种意义上,它并没有指向它指向的东西,就像调用者所看到的那样。它只允许将某些相关数据与引用对象关联起来,当PhantomReference排队在其相关的ReferenceQueue中时,可以检查和操作这些数据。通常,从PhantomReference派生出一个类型,并在该派生类型中包含一些附加数据。不幸的是,要使用这样的派生类型需要一些向下转换。

在您的示例代码中,可以为ref引用(或者,如果您愿意,是“变量”)为空。相反,调用Reference#get()时获取的值可能为空。如果发现其为空,则为时已晚,引用对象已开始进入被回收的过程:

final String val = ref.get();
if (null != val)
{
  // "val" is now pinned strongly.
}
else
{
  // "val" is already ready to be collected.
}

0