アプローチ 2) をお勧めします。
アプローチ 1 は、基礎となるスレッド システム (特に UNIX の場合) によるランダムな覚醒に対して堅牢ではなく、独自のエラー処理を実装する必要もあります。
アプローチ 2 では、基になるものから抽象化Thread
し、Runnable
orを操作できますCallable
。
さらに、アプローチ 1) にはクロック ドリフトの問題があります。つまり、タスクの実行にゼロ以外の時間がかかるため、10 秒ごとに実行されません。は、ScheduledExecutorService
実際には 1 秒ごとに、または必要に応じて 10 秒間隔で実行をスケジュールします。
アプローチ 2) は、スレッドが一定期間何かを実行するようにスケジュールする簡単な方法を提供し、javadocの例に従ってスレッドを強制終了します。
最後に、カスタム スレッドをシャットダウンして、最後のタスクが終了するまで待機する方ExecutorSevice
がはるかに簡単です。executorService.shutdown()
executorService.awaitTermination()
注意したいことの 1 つは、javadoc のこの gem です - 「タスクの実行で例外が発生した場合、後続の実行は抑制されます」。これは、非常に注意する必要があるか、したがってサブクラス化する必要があることを意味try/catch
します(javadoc から取得):Callable
ScheduledExecutorService
public class MyScheduledExecutor extends ScheduledThreadPoolExecutor {
public MyScheduledExecutor(int corePoolSize) {
super(corePoolSize);
}
@Override
protected void afterExecute(Runnable r, Throwable t) {
super.afterExecute(r, t);
if (t == null && r instanceof Future<?>) {
try {
Object result = ((Future<?>) r).get();
} catch (CancellationException ce) {
t = ce;
} catch (ExecutionException ee) {
t = ee.getCause();
} catch (InterruptedException ie) {
Thread.currentThread().interrupt(); // ignore/reset
}
}
if (t != null) {
System.out.println(t);
}
}
}