3 回答

TA貢獻(xiàn)1942條經(jīng)驗(yàn) 獲得超3個(gè)贊
即使異常名稱強(qiáng)烈建議也不是內(nèi)存問題,而是操作系統(tǒng)資源問題。您用完了本機(jī)線程,即操作系統(tǒng)將允許您的JVM使用多少線程。
這是一個(gè)不常見的問題,因?yàn)槟苌傩枰敲炊?。您是否有很多無(wú)條件線程產(chǎn)生,這些線程應(yīng)該在哪里出現(xiàn)但未完成?
您可能會(huì)考慮盡可能在執(zhí)行器的控制下重寫為使用Callable / Runnables。有許多行為可以由您的代碼輕松控制的標(biāo)準(zhǔn)執(zhí)行程序。
(有許多原因限制了線程數(shù),但是它們因操作系統(tǒng)而異)

TA貢獻(xiàn)1906條經(jīng)驗(yàn) 獲得超3個(gè)贊
在負(fù)載測(cè)試期間遇到了相同的問題,原因是由于JVM無(wú)法進(jìn)一步創(chuàng)建新的Java線程。以下是JVM源代碼
if (native_thread->osthread() == NULL) {
// No one should hold a reference to the 'native_thread'.
delete native_thread;
if (JvmtiExport::should_post_resource_exhausted()) {
JvmtiExport::post_resource_exhausted(
JVMTI_RESOURCE_EXHAUSTED_OOM_ERROR |
JVMTI_RESOURCE_EXHAUSTED_THREADS,
"unable to create new native thread");
} THROW_MSG(vmSymbols::java_lang_OutOfMemoryError(), "unable to create new native thread");
} Thread::start(native_thread);`
根本原因:當(dāng)JVMTI_RESOURCE_EXHAUSTED_OOM_ERROR(資源耗盡(意味著內(nèi)存耗盡))或JVMTI_RESOURCE_EXHAUSTED_THREADS(線程耗盡)時(shí),JVM引發(fā)此異常。
在我的情況下,Jboss創(chuàng)建了太多線程來(lái)滿足請(qǐng)求,但是所有線程都被阻塞了。因此,JVM耗盡了線程和內(nèi)存(每個(gè)線程都保存了memory,因?yàn)槊總€(gè)線程都被阻塞,所以不釋放內(nèi)存)。
分析Java線程轉(zhuǎn)儲(chǔ)后,發(fā)現(xiàn)有將近61K線程被我們的方法之一阻塞,這導(dǎo)致了此問題。以下是線程轉(zhuǎn)儲(chǔ)的一部分
"SimpleAsyncTaskExecutor-16562" #38070 prio=5 os_prio=0 tid=0x00007f9985440000 nid=0x2ca6 waiting for monitor entry [0x00007f9d58c2d000]
java.lang.Thread.State: BLOCKED (on object monitor)

TA貢獻(xiàn)2011條經(jīng)驗(yàn) 獲得超2個(gè)贊
您的操作系統(tǒng)可能不允許您嘗試創(chuàng)建的線程數(shù),或者您在JVM中達(dá)到了一定的限制。特別是如果它是一個(gè)32k的整數(shù),則很可能是一種或另一種限制。
您確定您確實(shí)需要32k線程嗎?大多數(shù)現(xiàn)代語(yǔ)言都對(duì)可重用線程池提供了某種支持-我確定Java也已經(jīng)具備了一些功能(例如ExecutorService
,如用戶Jesper所述)。也許您可以從這樣的池中請(qǐng)求線程,而不是手動(dòng)創(chuàng)建新線程。
添加回答
舉報(bào)