我有一個ExecutorService管理許多Callables。 Callables運行的任務主要是黑匣子轉換和數字運算。在某些情況下,正在轉換的數據會振盪,線程將花費一個多小時才能完成。爲了比較,大多數線程在一分鐘內完成。使用ExecutorService的個別線程的時間限制
長期運行的線程的數據並不相關,我想中斷任何運行時間超過一定時間的線程。什麼是最好的方式來做到這一點?
我有一個ExecutorService管理許多Callables。 Callables運行的任務主要是黑匣子轉換和數字運算。在某些情況下,正在轉換的數據會振盪,線程將花費一個多小時才能完成。爲了比較,大多數線程在一分鐘內完成。使用ExecutorService的個別線程的時間限制
長期運行的線程的數據並不相關,我想中斷任何運行時間超過一定時間的線程。什麼是最好的方式來做到這一點?
當達到超時時,使用ScheduleExecutorService將任務安排到taskFuture.cancel(true)
長時間運行的任務。如果任務在此之前完成,則不會被取消。
ExecutorService service = Executors.newFixedThreadPool(N);
ScheduledExecutorService canceller = Executors.newSingleThreadScheduledExecutor();
public <T> Future<T> executeTask(Callable<T> c, long timeoutMS){
final Future<T> future = service.submit(c);
canceller.schedule(new Callable<Void>(){
public Void call(){
future.cancel(true);
return null;
}
}, timeoutMS, TimeUnit.MILLI_SECONDS);
return future;
}
要做到這一點,最好的方法是引入一個Executor。您可以使用ScheduledExecutorService的取消所有長時間運行的任務,例如:
ExecutorService service = Executors.newFixedThreadPool(N);
ScheduledExecutorService canceller = Executors.newScheduledThreadPool(1);
public void executeTask(Callable<?> c){
final Future<?> future = service.submit(c);
canceller.schedule(new Runnable(){
public void run(){
future.cancel(true);
}
}, SECONDS_UNTIL_TIMEOUT, TimeUnit.SECONDS);
}
你可以(當你提交一個Callable創建的),其啓動時間,讓你的相應期貨的名單一起。
然後,另一個任務可以檢查每分鐘是否有某個任務運行超過了定義的時間,如果是,則在未來調用cancel(true)。完成期貨將從名單中刪除。
您可以使用此方法
<T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks,
long timeout,
TimeUnit unit)
throws InterruptedException
和最大超時設置爲一分鐘。如果你的線程需要更多,它只是中止。
您可以取消未來等在其他答案,但你需要確保你的線程是「數字計算」可以處理中斷並優雅地終止。你說這是一個黑匣子操作 - 你有多確定線程的中斷狀態正在黑匣子中被主動檢查?如果不是,則不能用中斷取消它。黑盒子需要在中斷的情況下書寫。
調用需要返回一個值。 – 2011-01-27 17:58:17
謝謝,你可以想象我只是自由寫作而已。如果只有Firefox有內置編譯器:) – 2011-01-27 17:59:51