0

我有一個java程序,產生4線程。在每個線程中,我有多個套接字超時。但是,這些超時似乎不受尊重,即readLine()功能可能會阻塞較長時間。在Java中有多個線程不遵守套接字超時?

我想要以下行爲:如果我將套接字超時設置爲300毫秒,那麼我希望readLine()函數在調用readLine()(即底層選擇調用)後的300毫秒內返回,無論如何。我知道OS調度程序會在進行處理器共享時將線程置於睡眠狀態,但是Java中是否有任何方式來強制線程始終被喚醒以確保這種行爲?或者,這是不是在多線程編程時想的正確方法?理想情況下,由於我生成了4個線程並在6核機器上運行,因此每個線程都應該能夠獲得自己的CPU並行運行,並遵守選擇的超時時間......但這可能太多了以期望...

PS:我實際上確實使用Thread.interrupt()來確保我的每個線程在一定的時間內退出(我檢查主線程中的時間,並中斷子線程,如果它的太長了)。在我的每個線程中,我連接到(不同的)服務器,發出請求並等待響應。我不知道答覆會持續多久。所以我一直在調用readLine()方法,直到它用SocketTimeoutException超時。我強制執行300 ms的超時,因爲我希望服務器在此時間內開始響應。我想強制執行此超時的原因是服務器以廣播方式運行,並將響應發送給所有客戶端的單個客戶端的請求。所以如果我沒有超時,我會繼續獲取數據來回應其他客戶的請求。

+0

超過300毫秒的線程是否超時後返回的線程? – SimonJ 2011-05-03 00:12:52

回答

0

您在這裏做一些錯誤的假設:

  • 的超時將完全爲300ms。事實上,超時時間將至少爲300ms。
  • OS調度程序在java線程中不執行任何操作(而不是調度java os進程)。
  • 擁有6個核心,並不意味着你的每個線程都會在單獨的核心上運行,所以不可能在java
  • 上綁定thread-> core,因爲你認爲jvm只有你的4個線程運行,但實際上有更多的線程,例如垃圾收集器線程。

問你的問題:「有沒有在Java中的任何方式來強制線程總是被喚醒,以確保這種行爲」 是的,這取決於它如何是你的代碼,如果線程是的Thread.Sleep (),您可以使用了Thread.interrupt()(一行readline()使用它),並辦理InterruptionException或者如果他們的Object.wait(),您可以使用object.notify()object.notifyAll()

+0

感謝您的回答。但是,我正在尋找類似於上面所述的bacchus的信息。如果問題不明確,我表示歉意。 – user10 2011-05-03 14:26:47

1

如果我真的瞭解您的問題,您可以隨時嘗試在執行readLine()操作的線程中調用Thread.interrupt()。由於您沒有提供任何代碼,我留下這link供您閱讀。這是一般的,但它提供了關於中斷線程的足夠信息。

這兩個鏈接也可能對您有用:How do you kill a thread in Java?How to abort a thread in a fast and clean way in java?

關於您關於操作系統調度程序的問題,您應該知道,在通用操作系統中,您沒有完全控制操作系統調度任務的方式。例如,在Linux中,中斷是最高優先級的任務,然後是調度策略,使您能夠對任務的調度方式進行「一些」決定。在Java中,您可以使用setPriority()方法來更改線程的優先級,但實際上它與使用nice命令相同,但您仍然無法保證此線程將在其他OS線程之前進行調度。

我希望這會有所幫助。

+0

感謝您的回覆!我編輯了我的問題以便給出一些背景並使其更清楚(只是添加了一個PS)。我不想中止線程,但在線程內,我想確保在合理的時間內從某個函數調用返回。 – user10 2011-05-03 00:00:21

+1

@gveda你可以計算你在'readLine()'方法上花費的時間,然後'break'正在使用它的循環。這不太好,但我認爲它解決了你的問題。 – bacchus 2011-05-03 00:23:25

+0

我最終做了類似的事情。我將初始超時設置爲300,然後一旦我開始獲取數據,就將超時設置爲更小的值(50)。謝謝! – user10 2011-05-03 14:23:25