この質問があります:
私はタイマーを持っています。scheduleAtFixedRate を使用すると、新しいタイマー タスクが作成されます。そのタイマー タスクには、完了するまでに時間がかかる特定のコードがあります。前のタスクがまだ完了していないときにタイマーが新しいタスクを作成しないようにするにはどうすればよいですか?
ありがとう
この質問があります:
私はタイマーを持っています。scheduleAtFixedRate を使用すると、新しいタイマー タスクが作成されます。そのタイマー タスクには、完了するまでに時間がかかる特定のコードがあります。前のタスクがまだ完了していないときにタイマーが新しいタスクを作成しないようにするにはどうすればよいですか?
ありがとう
私の答えは、使用しないことTimer
です。それは時代遅れです。Java5 以降、はるかに柔軟で使いやすい にTimer
取って代わられました。ScheduledExecutorService
スケジューラーがどのように機能するかをより細かく制御できますTimer
。
多数のファクトリ メソッドを持つExecutorsファクトリ クラスを使用して作成します。あなたが見るべきものはnewSingleThreadScheduledExecutorで、あなたが探しているものを正確に実行するはずです:
指定された遅延後にコマンドを実行するか、定期的に実行するようにコマンドをスケジュールできるシングルスレッド エグゼキューターを作成します。タスクは順次実行されることが保証されており、一度に複数のタスクがアクティブになることはありません。
をサブクラス化するScheduledExecutorService
代わりに、 を直接TimerTask
サブクラス化Runnable
し、タスクをエグゼキュータに送信します。エグゼキューターにはさまざまなメソッドがあり、ニーズに適したものを選択する必要があります (javadoc をScheduledExecutorService
注意深く読んでください) が、要点は次のようなものです。
// initialise the executor
ScheduledExecutorService executor = Executors.newSingleThreadScheduledExecutor();
while (tasksRemaining) {
// create your task
Runnable task = ....;
// submit it to the executor, using one of the various scheduleXYZ methods
executor.schedule(task, delay, unit);
}
// when everything is finished, shutdown the executor
executor.shutdown();
いつものように、javadoc を読んでください。
Timer クラスのドキュメント
各 Timer オブジェクトに対応するのは、タイマーのすべてのタスクを順番に実行するために使用される単一のバックグラウンド スレッドです。タイマー タスクはすぐに完了する必要があります。タイマー タスクの完了に時間がかかりすぎると、タイマーのタスク実行スレッドが「占有」されます。これにより、後続のタスクの実行が遅延する可能性があり、問題のあるタスクが最終的に完了すると、「まとまり」、立て続けに実行される可能性があります。
は、バックグラウンド スレッドが1 つしかないことを示しています。したがって、このシナリオは発生しないと思います。