8.1 Java 中的弱引用

Java 中有多種引用。

StrongReference - 這些是我們每天創建的最常見的鏈接。

Object object = new Object();//created an object
object = null;//can now be garbage collected

並且存在三種“特殊”類型的鏈接——SoftReference、WeakReference、PhantomReference。事實上,所有類型的鏈接之間只有一個區別 - GC 的行為及其所引用的對象。稍後我們將更詳細地討論每種鏈接類型的細節,但就目前而言,以下知識就足夠了:

  • SoftReference是一種軟引用,如果 GC 發現一個對像只能通過一系列軟引用訪問,那麼它將把它從內存中移除。或許。
  • WeakReference - 弱引用,如果 GC 發現一個對像只能通過弱引用鏈訪問,那麼它將把它從內存中移除。
  • PhantomReference是一個幻影引用,如果 GC 發現一個對像只能通過一串幻影引用鏈獲得,那麼它將把它從內存中移除。經過幾次 GC。

您也可以說鏈接類型具有一定程度的柔軟性:

  • 常規硬鏈接是引用類型的任何變量。在未使用之前未被垃圾收集器清理。
  • 軟參考。該對像不會導致所有內存用完 - 它保證在 OutOfMemoryError 發生之前被刪除。可能更早,這取決於垃圾收集器的實現。
  • 弱引用。柔弱些。不阻止對像被處理;垃圾收集器忽略此類引用。
  • 幻影參考。用於對象的“死亡”處理:對像在終結後可用,直到被垃圾回收。

如果尚不清楚區別是什麼,請不要擔心,很快一切都會水到渠成。細節在細節中,細節在後面。

8.2 Java 中的弱引用和軟引用

首先我們來看一下Java中的弱引用軟引用的區別。

簡而言之,如果只有弱引用指向對象,垃圾收集器將釋放該對象的內存。如果對象由 SoftReferences 指向,那麼當 JVM 急需內存時,內存將被釋放。

在某些情況下,這使SoftReference比 Strong reference具有明顯的優勢。例如,SoftReference 用於實現應用程序緩存,因此 JVM 要做的第一件事就是刪除只有 SoftReferences 指向的對象。

WeakReference非常適合存儲元數據,例如存儲對 ClassLoader 的引用。如果沒有加載任何類,則不應引用 ClassLoader。這就是為什麼 WeakReference 使得垃圾收集器可以在對它的最後一個強引用被刪除後立即在 ClassLoader 上完成它的工作。

Java 中的弱引用示例:

// some object
Student student = new Student();

// weak reference to it
WeakReference weakStudent = new WeakReference(student);

// now the Student object can be garbage collected
student = null;

Java 中的軟引用示例:

// some object
Student student = new Student();

// weak reference to it
SoftReference softStudent = new SoftReference(student)

// now the Student object can be garbage collected
// but this will only happen if the JVM has a strong need for memory
student = null;

8.3 Java 中的 PhantomReference

PhantomReference 實例的創建方式與 WeakReference 和 SoftReference 示例中的相同,但很少使用。

如果對像沒有強引用 (Strong)、弱引用 (WeakReference) 或軟引用 (SoftReference),則 PhantomReference 可以被垃圾回收。

您可以像這樣創建一個 Phantom Reference 對象:

PhantomReference myObjectRef = new PhantomReference(MyObject);

PhantomReference可用於 finalize() 沒有意義的情況。此引用類型與其他類型不同,因為它不是為訪問對象而設計的。這是一個信號,表明該對像已經完成,垃圾收集器已準備好回收其內存。

為此,垃圾收集器將它放在一個特殊的ReferenceQueue中以供進一步處理。ReferenceQueue 是放置對象引用以釋放內存的地方。

幻象引用是一種安全的方式來知道一個對像已經從內存中移除。例如,考慮一個處理大圖像的應用程序。假設我們想要在內存中已經準備好進行垃圾回收的圖像時將其加載到內存中。在這種情況下,我們希望在將新圖像加載到內存之前等待垃圾收集器殺死舊圖像。

這裡 PhantomReference 是一個靈活而安全的選擇。舊圖像對像被銷毀後,舊圖像的引用將傳遞給 ReferenceQueue。一旦我們有了這個鏈接,我們就可以將新圖像加載到內存中。

undefined
3
Опрос
Working with memory in Java,  18 уровень,  7 лекция
недоступен
Working with memory in Java
Working with memory in Java