問題來自一個(gè)線上GC頻繁的應(yīng)用,觀察到老年代一直gc下不去導(dǎo)致應(yīng)用被gc STW卡主假死,檢查代碼發(fā)現(xiàn)這樣一段代碼,感覺可疑
代碼如下:
public class WriteEsWork {
public static void write(List<EsIndexInfo> esList, String index, ESClusterEnum cluster, Worker worker) {
execServer.submit(new WriteESRunnable(esList, index, cluster, worker));
}
private static class WriteESRunnable implements Runnable {
private List<EsIndexInfo> esList;
...
}
}
jmap查到WriteESRunnable 這個(gè)對(duì)象有不少8000多個(gè),一個(gè)對(duì)象等于一個(gè)線程,EsIndexInfo這個(gè)對(duì)象也很多。
問題:WriteESRunnable 是一個(gè)靜態(tài)內(nèi)部類,這個(gè)類只會(huì)在靜態(tài)方法write被調(diào)用的時(shí)候 new對(duì)象到線程池,那么當(dāng)這個(gè)線程執(zhí)行完成后,WriteESRunnable 對(duì)象會(huì)被釋放嗎?還是因?yàn)樗莾?nèi)部靜態(tài)類會(huì)一直保留引用?如果不釋放就說明確實(shí)是因?yàn)檫@個(gè)問題導(dǎo)致WriteESRunnable 和EsIndexInfo對(duì)象堆積太久。
如果釋放的話 那就是另一種可能 線程再線程池等待隊(duì)列堆積的太多了。
還請(qǐng)朋友們幫忙分析!謝謝
1 回答

倚天杖
TA貢獻(xiàn)1828條經(jīng)驗(yàn) 獲得超3個(gè)贊
根據(jù)你的代碼片段,只有線程池持有對(duì)[new WriteESRunnable]的引用,所以第二情況可能性比較大。
每個(gè)任務(wù)的處理太長, 任務(wù)隊(duì)列沒有限制導(dǎo)致過長,然后就發(fā)生堆積情況了。
添加回答
舉報(bào)
0/150
提交
取消