Java Reference家族

Reference家族

https://www.zhihu.com/question/62953438?from=profile_question_card

父類特性

整體邏輯蚯瞧,JVM將待回收對象對應(yīng)的Reference對象放入pending列表,由ReferenceHandler將pending列表中的對象取出放入ReferenceQueue,以此作為一個通知機(jī)制忽舟。

Reference next;

Reference類型的對象類似鏈表的節(jié)點(diǎn)淮阐,每個Reference類型的對象持有下一個Reference類型的對象的引用叮阅,這樣組成了單向鏈表(ReferenceQueue實(shí)際節(jié)點(diǎn))。

private static Reference<Object> pending = null;

static字段泣特,整個JVM只有唯一的一個浩姥。JVM的垃圾回收器會將所有被標(biāo)記對象對應(yīng)的Reference類型的對象添加到這里,組成Reference類型的對象的單向鏈表状您,這一步是JVM做的勒叠。

private static class ReferenceHandler extends Thread;

內(nèi)部類線程镀裤,在Reference的static代碼塊創(chuàng)建,JVM全局唯一缴饭。

public void run() {

            while (true) {

                tryHandlePending(true);

            }

        }

### static boolean tryHandlePending(boolean waitForNotify)

不斷從pending上的Reference類型的對象的單向鏈表上取出Reference類型對象,然后將改Reference類型對象放入Reference類型的對象自帶的ReferenceQueue中骆莹。

如果Reference類型對象是Cleaner颗搂,調(diào)用Cleaner的clean()方法。

子類

SoftReference

WeakReference

  • WeakHashMap(應(yīng)用)

    通過查詢queue中的數(shù)據(jù)幕垦,判斷是否有對象被回收丢氢,被回收則刪除map中對應(yīng)的key。

  • ThreadLocalMap(應(yīng)用)

    構(gòu)造WeakReference對象時未傳入queue先改,通過不斷調(diào)用get()方法判斷是否為null來確定對象是否被回收疚察。

PhantomReference

Finalizer vs. Cleaner

因?yàn)镕inalizer也是一種Reference,所以前邊Reference的處理邏輯是和Weak, Soft reference的邏輯十分相似的仇奶。

而且Finalizer和Cleaner的作用也十分相似貌嫡,但有一個巨大的不同在于,finalize方法里可以使object 復(fù)活该溯,而 Cleaner 的 clean 方法中不能使得對象復(fù)活岛抄。

這是因?yàn)?finalize 中,可以通過 this 指針訪問到 object 對象狈茉,例如:

public void finalize() {

    Other.ref = this;

}

這樣的話夫椭,一個本來應(yīng)該被回收的對象又在finalize之后復(fù)活了。但是Cleaner為什么不行呢氯庆?因?yàn)樗幕愂且粋€PhantomReference蹭秋,這個“鬼引用”的 get 方法是這樣的:

public class PhantomReference<T> extends Reference<T> {

    public T get() {

        return null;

    }

    // 其它代碼略

}

永遠(yuǎn)返回null,也就是說對于Cleaner堤撵,創(chuàng)建了以后仁讨,就再也不能訪問它的referent了。

  • Cleaner(子類)

  • DirectByteBuffer(應(yīng)用)

  • private static Cleaner first = null;

    Cleaner.create方法會將Cleaner對象加到一個雙向鏈表中去粒督,這樣做是為了保證在referent被回收之前這些Cleaner都是存活的陪竿。

FinalReference

FinalReference僅僅繼承了Reference,沒有做其他的邏輯屠橄,只是將訪問權(quán)限聲明為package族跛,所以我們不能夠直接使用它。

  • Finalizer(子類)

    只要類覆寫了Object 上的finalize方法锐墙,方法體非空礁哄。那么這個類的實(shí)例都會被Finalizer引用類型引用。這個工作是由虛擬機(jī)完成的溪北,對于我們來說是透明的桐绒。

    覆蓋了finalize方法的對象至少需要兩次GC才可能被回收夺脾。第一次GC把覆蓋了finalize方法的對象對應(yīng)的Finalizer reference加入referenceQueue等待FinalizerThread來執(zhí)行finalize方法。第二次GC才有可能釋放finalizee對象本身茉继,前提是FinalizerThread已經(jīng)執(zhí)行完finalize方法了咧叭,并把Finalizer reference從Finalizer靜態(tài)unfinalized鏈表中剔除,因?yàn)檫@個鏈表和Finalizer reference對finalizee構(gòu)成的是一個強(qiáng)引用烁竭。

- private static ReferenceQueue queue = new ReferenceQueue();

- private static Finalizer unfinalized;

維護(hù)了一個未執(zhí)行finalize方法的reference列表菲茬。維護(hù)靜態(tài)字段unfinalized的目的是為了一直保持對未未執(zhí)行finalize方法的reference的強(qiáng)引用,防止被gc回收掉派撕。

- private static class FinalizerThread extends Thread;

Finalizer靜態(tài)代碼塊里啟動了一個deamon線程 FinalizerThread婉弹,F(xiàn)inalizerThread run方法不斷的從queue中去取Finalizer類型的reference,然后調(diào)用Finalizer的runFinalizer方法终吼,該方法最后執(zhí)行了referent所重寫的finalize方法镀赌。finalize方法執(zhí)行之后移除unfinalized列表。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末际跪,一起剝皮案震驚了整個濱河市商佛,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌垫卤,老刑警劉巖威彰,帶你破解...
    沈念sama閱讀 211,561評論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異穴肘,居然都是意外死亡歇盼,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,218評論 3 385
  • 文/潘曉璐 我一進(jìn)店門评抚,熙熙樓的掌柜王于貴愁眉苦臉地迎上來豹缀,“玉大人,你說我怎么就攤上這事慨代⌒象希” “怎么了?”我有些...
    開封第一講書人閱讀 157,162評論 0 348
  • 文/不壞的土叔 我叫張陵侍匙,是天一觀的道長氮惯。 經(jīng)常有香客問我,道長想暗,這世上最難降的妖魔是什么妇汗? 我笑而不...
    開封第一講書人閱讀 56,470評論 1 283
  • 正文 為了忘掉前任,我火速辦了婚禮说莫,結(jié)果婚禮上杨箭,老公的妹妹穿的比我還像新娘。我一直安慰自己储狭,他們只是感情好互婿,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,550評論 6 385
  • 文/花漫 我一把揭開白布捣郊。 她就那樣靜靜地躺著,像睡著了一般慈参。 火紅的嫁衣襯著肌膚如雪呛牲。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,806評論 1 290
  • 那天驮配,我揣著相機(jī)與錄音侈净,去河邊找鬼。 笑死僧凤,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的元扔。 我是一名探鬼主播躯保,決...
    沈念sama閱讀 38,951評論 3 407
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼澎语!你這毒婦竟也來了途事?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,712評論 0 266
  • 序言:老撾萬榮一對情侶失蹤擅羞,失蹤者是張志新(化名)和其女友劉穎尸变,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體减俏,經(jīng)...
    沈念sama閱讀 44,166評論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡召烂,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,510評論 2 327
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了娃承。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片奏夫。...
    茶點(diǎn)故事閱讀 38,643評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖历筝,靈堂內(nèi)的尸體忽然破棺而出酗昼,到底是詐尸還是另有隱情,我是刑警寧澤梳猪,帶...
    沈念sama閱讀 34,306評論 4 330
  • 正文 年R本政府宣布麻削,位于F島的核電站,受9級特大地震影響春弥,放射性物質(zhì)發(fā)生泄漏呛哟。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,930評論 3 313
  • 文/蒙蒙 一惕稻、第九天 我趴在偏房一處隱蔽的房頂上張望竖共。 院中可真熱鬧,春花似錦俺祠、人聲如沸公给。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,745評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽淌铐。三九已至肺然,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間腿准,已是汗流浹背际起。 一陣腳步聲響...
    開封第一講書人閱讀 31,983評論 1 266
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留吐葱,地道東北人街望。 一個月前我還...
    沈念sama閱讀 46,351評論 2 360
  • 正文 我出身青樓,卻偏偏與公主長得像弟跑,于是被迫代替她去往敵國和親灾前。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,509評論 2 348