Java中的四種引用方式(強引用、軟引用、弱引用、虛引用)
強引用(StrongReference)
強引用就是指在程式程式碼之中普遍存在的,比如下面這段程式碼中的object和str都是強引用:
Object object = new Object();
String str = “hello”;
只要某個物件有強引用與之關聯,JVM必定不會回收這個物件,即使在記憶體不足的情況下,JVM寧願丟擲OutOfMemory錯誤也不會回收這種物件。比如下面這段程式碼:
public class Main {
public static void main(String[] args) {
new Main().fun1();
}
public void fun1() {
Object object = new Object();
Object[] objArr = new Object[1000];
}
}
當執行至Object[] objArr = new Object[1000];這句時,如果記憶體不足,JVM會丟擲OOM錯誤也不會回收object指向的物件。不過要注意的是,當fun1執行完之後,object和objArr都已經不存在了,所以它們指向的物件都會被JVM回收。
如果想中斷強引用和某個物件之間的關聯,可以顯示地將引用賦值為null,這樣一來的話,JVM在合適的時間就會回收該物件。
軟引用(SoftReference)
軟引用是用來描述一些有用但並不是必需的物件,在Java中用java.lang.ref.SoftReference類來表示。對於軟引用關聯著的物件,只有在記憶體不足的時候JVM才會回收該物件。因此,這一點可以很好地用來解決OOM的問題,並且這個特性很適合用來實現快取:比如網頁快取、圖片快取等。
軟引用可以和一個引用佇列(ReferenceQueue)聯合使用,如果軟引用所引用的物件被JVM回收,這個軟引用就會被加入到與之關聯的引用佇列中。下面是一個使用示例:
import java.lang.ref.WeakReference;
public class Main {
public static void main(String[] args) {
WeakReference<String> sr = new WeakReference<String>(new String("hello"));
System.out.println(sr.get());
System.gc(); //通知JVM的gc進行垃圾回收
System.out.println(sr.get());
}
}
弱引用(WeakReference)
弱引用也是用來描述非必需物件的,當JVM進行垃圾回收時,無論記憶體是否充足,都會回收被弱引用關聯的物件。在java中,用java.lang.ref.WeakReference類來表示。下面是使用示例:
import java.lang.ref.WeakReference;
public class Main {
public static void main(String[] args) {
WeakReference<String> sr = new WeakReference<String>(new String("hello"));
System.out.println(sr.get());
System.gc(); //通知JVM的gc進行垃圾回收
System.out.println(sr.get());
}
}
虛引用(PhantomReference)
虛引用和前面的軟引用、弱引用不同,它並不影響物件的生命週期。在java中用java.lang.ref.PhantomReference類表示。如果一個物件與虛引用關聯,則跟沒有引用與之關聯一樣,在任何時候都可能被垃圾回收器回收。
要注意的是,虛引用必須和引用佇列關聯使用,當垃圾回收器準備回收一個物件時,如果發現它還有虛引用,就會把這個虛引用加入到與之 關聯的引用佇列中。程式可以通過判斷引用佇列中是否已經加入了虛引用,來了解被引用的物件是否將要被垃圾回收。如果程式發現某個虛引用已經被加入到引用佇列,那麼就可以在所引用的物件的記憶體被回收之前採取必要的行動。
進一步理解軟引用和弱引用
對於強引用,我們平時在編寫程式碼時經常會用到。而對於其他三種型別的引用,使用得最多的就是軟引用和弱引用,這2種既有相似之處又有區別。它們都是用來描述非必需物件的,但是被軟引用關聯的物件只有在記憶體不足時才會被回收,而被弱引用關聯的物件在JVM進行垃圾回收時總會被回收。針對上面的特性,軟引用適合用來進行快取,當記憶體不夠時能讓JVM回收記憶體,弱引用能用來在回撥函式中防止記憶體洩露。因為回撥函式往往是匿名內部類,隱式儲存有對外部類的引用,所以如果回撥函式是在另一個執行緒裡面被回撥,而這時如果需要回收外部類,那麼就會記憶體洩露,因為匿名內部類儲存有對外部類的強引用。
相關文章
- Java四種引用包括強引用,軟引用,弱引用,虛引用。Java
- Java的強引用、軟引用、弱引用、虛引用Java
- Java/Android中的強引用、軟引用、弱引用、虛引用JavaAndroid
- Java四大引用詳解:強引用、軟引用、弱引用、虛引用Java
- 強引用 軟引用 弱引用 虛引用
- 強引用,軟引用,弱引用,虛引用
- 強引用、軟引用、弱引用、虛引用
- 理解Java的強引用、軟引用、弱引用和虛引用Java
- 強引用、軟引用、弱引用與虛引用
- 【JVM】如何理解強引用、軟引用、弱引用、虛引用?JVM
- Java 中的強引用、軟引用、弱引用和虛引用分別是什麼?Java
- Java常見知識點彙總(⑲)——Java中的強引用、弱引用、軟引用、虛引用Java
- java的強引用、軟引用、弱引用、幻象引用,引用佇列總結Java佇列
- Java引用型別解析:掌握強引用、軟引用、弱引用和幻象引用的妙用Java型別
- Java中強、軟、弱、虛四種引用詳解Java
- 強引用、軟引用、弱引用、幻象引用有什麼區別?
- 強引用、軟引用、弱引用、幻象引用再不理解就晚了
- 關於強引用、軟引用、弱引用、幻象引用,你該如何回答?
- 老徐和阿珍的故事:強引用、軟引用、弱引用、虛引用,傻傻分不清楚
- Java中的弱引用Java
- Java的四種引用Java
- 垃圾回收(四)【弱引用】
- python3學習筆記之 強引用和弱引用Python筆記
- Java 四種引用的解讀Java
- Java中的引用Java
- 安卓四種引用安卓
- Java的四種引用和回收策略Java
- java中的引用物件Java物件
- Java 中的方法引用Java
- 面試官:說說Java物件的四種引用方式面試Java物件
- 詳聊Java的四種引用型別Java型別
- 引用以及引用的實質
- 十分鐘理解Java中的弱引用Java
- sed中變數引用的幾種方式變數
- 引用
- Swift 4 弱引用實現Swift
- Java中的引用與ThreadLocalJavathread
- Java中的四大引用筆記Java筆記
- JVM 符號引用和直接引用JVM符號