0

Queueに100個のRunnableオブジェクトがあるとします。固定サイズ(例えば10)のExecutorServicePoolを使用する場合、Queueから次のRunnableオブジェクトを実行するために少なくとも10スレッドのうちの1つを終了する必要があります。特定の時間間隔の後にキューから次のRunnableをスケジュールして、ラウンドロビン方式のようにQueueの最後に保存する現在のRunnable状態を保存する方法はありますか?状態を保存している間にThreadPoolでマルチスレッドする

+0

本当の目標は何ですか?あなたが描いている状況よりも良い方法があるかもしれません。 – corsiKa

+0

まだ実行中の場合、一定期間後にプール内のスレッドを取得したいのですか? –

+0

スレッドを終了する必要はありません(終了しない)。ランニングシューズの1つが終了する必要があります。あなたは何を達成しようとしていますか? – Kayaman

答えて

0

私は特定のインターバルの後にキューから次のRunnableをスケジュールし、ややラウンドロビン方式のようにキューの最後に保存されるように、現在のRunnable状態を保存することができ、他の方法はありますか?

私はここで質問を理解することを願っています。これがあなたの話ではない場合は、あなたの質問を編集して詳細を述べてください。

状態の保存については、ThreadLocalを使用して、エグゼキュータ・サービスで実行されている各スレッドがそれぞれの状態を保存できるようにするのが簡単な方法です。

private final ThreadLocal<State> stateThreadLocal = new ThreadLocal<>() { 
    // state initialization if needed 
    protected State initialValue() { return new State(); } 
}; 
... 
public void run() { 
    State state = stateThreadLocal.get(); 
    // now you can process the job with the state 
} 

しかし、この解決策は、あなたがHTTPクライアントか何かをクローズする必要がある場合は、状態が解除されたときに制御するための機会を与えるものではありません。

より良い解決策は、executor-serviceを使用して静的なワーカーリストを開始し、独自のBlockingQueueを使用してワーカーにジョブを注入することです。彼らは実行の間開催するローカル状態フィールドを開催する

private final static int NUM_WORKERS = 10; 
private final ExecutorService threadPool = Executors.newFixedThreadPool(NUM_WORKERS); 
... 

final BlockingQueue<Job> queue = new LinkedBlockingQueue<>(); 
for (int i = 0; i < NUM_WORKERS; i++) { 
    threadPool.submit(new WorkerWithState(queue)); 
} 
// shutdown the queue once the last worker is submitted 
threadPool.shutdown(); 
... 
// then you submit a number of jobs to your own queue for the workers with state to run 
queue.add(new Job(...)); 
... 

あなたの労働者:

は、たとえば次のような何かを行うことができます。

private class WorkerWithState implements Runnable { 
    // some state held by the worker 
    private SomeState state = new SomeState(); 
    private final BlockingQueue queue; 
    public WorkerWithState(BlockingQueue queue) { 
     this.queue = queue; 
    } 
    public void run() { 
     while (!Thread.currentThread().isInterrupted()) { 
     try { 
      // wait for a job to process 
      Job job = queue.take(); 
      // process the job here using the state 
      processJob(job, state); 
     } catch (InterruptedException ie) { 
      // always a good pattern 
      Thread.currentThread().interrupt(); 
      return; 
     } 
     } 
    } 
} 

これらの労働者を終了するために、あなたはそれらをすべて中断したり、ジョブキューが枯渇した後、彼らは自分自身を停止持つように一定のQUIT_JOBを注入するスレッドプールにthreadPool.shutdownAll(true)を呼び出すことができます。

関連する問題