0

でタスクを渡すExecutorService(または atm のサブクラス) があります。ThreadPoolExecutorServicesubmit(Runnable r)

実行中に同じタスクが (再) 送信される場合があり、最初の送信が完了するまで 2 番目の送信を待ちたいと思います。つまり、キューに入れました。それを行うにはどうすればよいでしょうか?送信されたタスクが既に実行されている場合にのみキューに入れ、それ以外の場合は直接実行する必要があります。

返さFuture<>れた s は、タスクをキャンセルするために使用されることがあります。

このようなもの;

    Runnable r = new LengthyRunnable();

    Future<?> f1 = submit(r); //should start to run
    Future<?> f2 = submit(r); //should be queued and wait for f1
    Future<?> f3 = submit(r); //in case f1 hasnt finished, and f2 is queued, should remove f2 from the queue and take it's place

私は ThreadPoolExecutorService をサブクラス化し、 beforeExecute と afterExecute を使用してタスクを追跡していますが、難しくなっています... a 以外のものを使用する必要がありThreadPoolExecutorServiceますか?

4

2 に答える 2

0

f3 がエンキューされ、f2 がまだ開始されていないときに、エンキューされた f2 タスクを削除したいとします。ただし、基になる実装が非同期でさえない可能性があるため、ExecutorService はキューへのアクセスを公開しません。ThreadPoolExecutor には基になるキューがありますが、実際には公開されていません:)

誰かが提案したように、単にスケジュール可能な /recurrent タスクを作成したくない場合は、次のことを検討してください。

WorkPerformer ランナブルを作成します。ある種の BlockingQueue、つまり LinkedBlockingQueue を渡します。キューは、実行する必要があるある種の LengthyTask をキューに入れるために使用されます。

呼び出しコードでは、キューを覗く同期ブロックを作成します。f2 がそこにあり、f1 がまだ実行中の場合 (WorkPerformer には何らかの同期フラグがある場合)、f2 をデキューし、f3 をエンキューします。

この背後にあるあなたの意図が何であるかを知らずに、これ以上/より良いものを提案することは困難です.

于 2013-01-14T21:41:04.763 に答える
0

LengthyRunnable再度実行する必要があるかどうかを確認する繰り返しタスクを (適切なプール間隔で)作成します。そうすれば、複数回実行されないようにすることができます。

于 2013-01-14T18:50:22.143 に答える