2013-04-08 51 views
1

如果應用程序在其代碼中的各個位置(包括從引用的jar中)啓動多個線程(使用new Thread()以及使用ExecutorService),那麼識別啓動任何特定線程的源代碼(如在應用程序的執行實例中所見)在大型應用程序的源代碼中跟蹤線程初始化

這很有幫助,例如,在線程導致Exception的情況下 - 我們需要從源代碼開始,初始化(以便上下文清晰)。我從VisualVM獲得的線程轉儲顯示許多運行/等待線程,但堆棧根似乎總是at java.lang.Thread.run(Thread.java:722) - 不是很有幫助。 `

+2

給他們所有獨特的名字怎麼樣? – Andremoniy 2013-04-08 18:07:39

+0

@Andremoniy這是一個好主意!但如果這是傳統代碼呢? – Eugene 2013-04-08 18:11:09

+0

許多線程名稱都是在代碼中生成的 - 對調試無用 – Bhaskar 2013-04-08 18:14:29

回答

0

你能夠在創建線程的地方插入代碼嗎?如果是這樣,那麼在您的主類中創建一個靜態HashMap以及一個公共靜態put方法。然後,無論何時創建線程t1,調用Main.putThreadId(t1.getId(),「標識創建線程的方法的一些文本」),以及在捕獲異常時查找HashMap中的值。

0

您可以做的是將Thread.uncaughtExceptionhandler設置爲您開始的每個線程。 它有一個名爲方法:

uncaughtException(Thread t,Throwable e) 

這裏面你可以把日誌或東西與以後可以從那裏此代碼要求確定。但是,對於每一個線程而言,您都必須單獨指定爲原點。

您可以通過Thread.setDefaultUncaughtExceptionHandler(myHandler);來設置全局。但爲了使它不同,可能有一個ThreadGroup或其他東西。

儘管如果線程由引用的Jar啓動,所有這些都沒有幫助。

0

您可以使用之前給出的映射方法,但不是在某些文本中,而是在創建線程的位置生成新的Exception。將此異常作爲值映射到地圖中。如果需要,您可以稍後獲取堆棧跟蹤。對於Executor s,您可以在創建工作線程的ThreadFactory中隱藏此項。

當使用Runnable s時,會出現類似的問題。有時,您想知道在run方法開始的任何堆棧跟蹤之上Runnable已創建並排隊的位置。

當然整個遺留代碼引用的JAR問題就是:你想解決,需要編碼的問題,但沒有編碼。不容易:)