Module java.base
Package java.lang.ref

Class Reference<T>

java.lang.Object
java.lang.ref.Reference<T>
类型参数:
T - 引用的类型
直接已知子类:
PhantomReference, SoftReference, WeakReference

public abstract sealed class Reference<T> extends Object permits PhantomReference<T>, SoftReference<T>, WeakReference<T> (not exhaustive)
引用对象的抽象基类。该类定义了所有引用对象共有的操作。由于引用对象与垃圾收集器紧密合作实现,因此该类不能直接被子类化。
封闭类层次图:
Reference的封闭类层次图Reference的封闭类层次图
自 JDK 版本:
1.2
  • Method Summary

    Modifier and Type
    Method
    Description
    void
    clear()
    清除此引用对象。
    protected Object
    clone()
    boolean
    清除此引用对象并将其添加到其注册的队列中(如果有)。
    T
    get()
    返回此引用对象的引用对象。
    boolean
    已弃用。
    该方法最初被指定为测试引用对象是否已被清除和入队,但从未实现执行此测试。
    static void
    确保给定引用引用的对象保持强引用,无论程序之前的任何操作可能导致对象变得不可访问;因此,被引用的对象至少在调用此方法之后的垃圾回收之前不可被垃圾回收。
    final boolean
    refersTo(T obj)
    测试此引用对象的引用对象是否为 obj

    Methods declared in class java.lang.Object

    equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
  • Method Details

    • get

      public T get()
      返回此引用对象的引用对象。如果此引用对象已被清除,无论是程序还是垃圾收集器清除,那么此方法将返回 null
      API 注释:
      此方法返回引用对象的强引用。这可能会导致垃圾收集器将其视为强引用,直到稍后的收集周期。可以使用 refersTo 方法来避免这种强化,当测试某个对象是否为引用对象的引用对象时;也就是说,使用 ref.refersTo(obj) 而不是 ref.get() == obj
      返回:
      此引用所指向的对象,如果此引用对象已被清除,则返回 null
      另请参阅:
    • refersTo

      public final boolean refersTo(T obj)
      测试此引用对象的引用对象是否为 obj。使用 nullobj 如果引用对象已被清除,则返回 true
      参数:
      obj - 与此引用对象的引用对象进行比较的对象
      返回:
      如果 obj 是此引用对象的引用对象,则返回 true
      自 JDK 版本:
      16
    • clear

      public void clear()
      清除此引用对象。调用此方法不会导致此对象被入队。

      此方法仅由 Java 代码调用;当垃圾收集器清除引用时,它会直接执行,而不调用此方法。

    • isEnqueued

      @Deprecated(since="16") public boolean isEnqueued()
      Deprecated.
      This method was originally specified to test if a reference object has been cleared and enqueued but was never implemented to do this test. This method could be misused due to the inherent race condition or without an associated ReferenceQueue. An application relying on this method to release critical resources could cause serious performance issue. An application should use ReferenceQueue to reliably determine what reference objects that have been enqueued or refersTo(null) to determine if this reference object has been cleared.
      测试此引用对象是否在其关联队列中。仅当满足以下所有条件时,此方法才返回 true
      • 此引用对象在创建时已注册到队列;并且
      • 垃圾收集器已将此引用对象添加到队列,或者已调用 enqueue();并且
      • 此引用对象尚未从队列中移除。
      否则,此方法返回 false。如果此引用对象已被清除但未入队,此方法可能返回 false,由于竞争条件。
      返回:
      true 仅当此引用对象在其关联队列中时。
    • enqueue

      public boolean enqueue()
      清除此引用对象并将其添加到其注册的队列中(如果有)。

      此方法仅由 Java 代码调用;当垃圾收集器将引用对象入队时,它会直接执行,而不调用此方法。

      返回:
      如果成功将此引用对象入队,则返回 true;如果已经入队或在创建时未注册到队列,则返回 false
    • clone

      protected Object clone() throws CloneNotSupportedException
      抛出 CloneNotSupportedException。一个 Reference 无法有实际意义地进行克隆。请构造一个新的 Reference
      覆盖:
      clone 在类 Object
      返回:
      永远不会正常返回
      抛出:
      CloneNotSupportedException - 总是
      自 JDK 版本:
      11
      另请参阅:
    • reachabilityFence

      public static void reachabilityFence(Object ref)
      确保给定引用引用的对象保持强引用,无论程序之前的任何操作可能导致对象变得不可访问;因此,被引用的对象至少在调用此方法之后的垃圾回收之前不可被垃圾回收。调用此方法本身不会启动垃圾回收或终结。

      此方法为强引用可达性建立了一种顺序,关于垃圾回收触发的可达性条件。它控制了程序中否则只有隐含的关系 -- 触发垃圾回收的可达性条件。此方法设计用于在过早终结的罕见情况下使用,其中使用 synchronized 块或方法,或使用其他同步设施不可行或无法提供所需的控制。此方法仅适用于可能对可见效果进行回收的对象,这对于具有终结器的对象是可能的(请参阅 The Java Language Specification 的第 12.6 节)这些对象以依赖于顺序控制的方式实现终结器。

      API 注释:
      当虚拟机检测到对象不会再存储在堆中时,终结可能会发生:即使该对象的字段仍在使用中,只要对象已变得不可访问,垃圾收集器就可以回收对象。在以下示例中,类的簿记通过数组索引进行管理。在这里,方法 action 使用 reachabilityFence 来确保在执行关联的 ExternalResource 的簿记之前不会回收 Resource 对象;特别是在这里,确保在方法 Object.finalize() 中不会并发运行,以避免将 ExternalResource 的数组槽置空。
       
       class Resource {
         private static ExternalResource[] externalResourceArray = ...
      
         int myIndex;
         Resource(...) {
           myIndex = ...
           externalResourceArray[myIndex] = ...;
           ...
         }
         protected void finalize() {
           externalResourceArray[myIndex] = null;
           ...
         }
         public void action() {
           try {
             // ...
             int i = myIndex;
             Resource.update(externalResourceArray[i]);
           } finally {
             Reference.reachabilityFence(this);
           }
         }
         private static void update(ExternalResource ext) {
           ext.status = ...;
         }
       }
      在这里,对 reachabilityFence 的调用被非直观地放置在 之后 调用 update,以确保在更新之前不会由 Object.finalize() 置空数组槽,即使调用 action 是此对象的最后使用。例如,如果用户程序中的用法形式为 new Resource().action();,则不会保留对此 Resource 的其他引用。虽然在这里可能有些过度,但 reachabilityFence 被放置在 finally 块中,以确保它在方法的所有路径中都被调用。在具有更复杂控制路径的方法中,您可能需要进一步的预防措施,以确保 reachabilityFence 在所有路径上都被遇到。

      有时可以更好地封装对 reachabilityFence 的使用。继续上面的示例,如果调用方法 update 即使终结器已经执行(置空槽)也可以继续,则可以局部化对 reachabilityFence 的使用:

       
       public void action2() {
         // ...
         Resource.update(getExternalResource());
       }
       private ExternalResource getExternalResource() {
         ExternalResource ext = externalResourceArray[myIndex];
         Reference.reachabilityFence(this);
         return ext;
       }

      在本身确保可达性的构造中,不需要方法 reachabilityFence。例如,因为被锁定的对象通常不能被回收,所以如果类 Resource 的所有方法(包括 finalize)中的所有对象访问都包含在 synchronized (this) 块中,那么就足够了。 (此外,这样的块不能包含无限循环,或者本身不可访问,这些属于“通常情况”免责声明的特例。)但是,在这种方法不那么高效、不那么可取或不可能的情况下,方法 reachabilityFence 仍然是更好的选择;例如,因为它可能会遇到死锁。

      参数:
      ref - 引用。如果为 null,则此方法不起作用。
      自 JDK 版本:
      9