モジュール java.base
パッケージ java.util.concurrent

クラスExchanger<V>

java.lang.Object
java.util.concurrent.Exchanger<V>
型パラメータ:
V - 交換されるオブジェクトの型

public class Exchanger<V> extends Object
スレッドをペアにして、ペア内の要素を交換できる同期ポイント。 各スレッドは、exchangeメソッドに入ると何らかのオブジェクトを提供し、パートナ・スレッドと照合して、復帰時にそのパートナのオブジェクトを受け取ります。 Exchangerは、SynchronousQueueの双方向形式として表示されることがあります。 Exchangerは、遺伝アルゴリズムやパイプライン設計などのアプリケーションで便利です。

使用例: ここでは、Exchangerを使用してスレッド間でバッファを交換するクラスのサマリーを示します。バッファを満たすスレッドが必要に応じて新しい空のスレッドを取得し、バッファを空にするスレッドに満たされたバッファを渡します。

 
 class FillAndEmpty {
   Exchanger<DataBuffer> exchanger = new Exchanger<>();
   DataBuffer initialEmptyBuffer = ...; // a made-up type
   DataBuffer initialFullBuffer = ...;

   class FillingLoop implements Runnable {
     public void run() {
       DataBuffer currentBuffer = initialEmptyBuffer;
       try {
         while (currentBuffer != null) {
           addToBuffer(currentBuffer);
           if (currentBuffer.isFull())
             currentBuffer = exchanger.exchange(currentBuffer);
         }
       } catch (InterruptedException ex) { ... handle ...}
     }
   }

   class EmptyingLoop implements Runnable {
     public void run() {
       DataBuffer currentBuffer = initialFullBuffer;
       try {
         while (currentBuffer != null) {
           takeFromBuffer(currentBuffer);
           if (currentBuffer.isEmpty())
             currentBuffer = exchanger.exchange(currentBuffer);
         }
       } catch (InterruptedException ex) { ... handle ...}
     }
   }

   void start() {
     new Thread(new FillingLoop()).start();
     new Thread(new EmptyingLoop()).start();
   }
 }

メモリー整合性効果: Exchangerを介してオブジェクトを正常に交換するスレッドの各ペアでは、各スレッド内のexchange()の前のアクションは、もう一方のスレッド内の対応するexchange()からの復帰に続くアクションの前に発生します。

導入されたバージョン:
1.5
  • コンストラクタのサマリー

    コンストラクタ
    コンストラクタ
    説明
    新しいExchangerを作成します。
  • メソッドのサマリー

    修飾子と型
    メソッド
    説明
    現在のスレッドは、割り込みが発生しないかぎり、もう一方のスレッドがこの交換ポイントに達するまで待機し、指定されたオブジェクトをそのスレッドに転送して、代わりにもう一方のスレッドのオブジェクトを受け取ります。
    exchange(V x, long timeout, TimeUnit unit)
    現在のスレッドは、割り込みが発生するか、指定された待機時間が経過しないかぎり、もう一方のスレッドがこの交換ポイントに達するまで待機し、指定されたオブジェクトをそのスレッドに転送して、代わりにもう一方のスレッドのオブジェクトを受け取ります。

    クラス java.lang.Objectで宣言されたメソッド

    clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
  • コンストラクタの詳細

    • Exchanger

      public Exchanger()
      新しいExchangerを作成します。
  • メソッドの詳細

    • exchange

      public V exchange(V x) throws InterruptedException
      現在のスレッドは、割り込みが発生しないかぎり、もう一方のスレッドがこの交換ポイントに達するまで待機し、指定されたオブジェクトをそのスレッドに転送して、代わりにもう一方のスレッドのオブジェクトを受け取ります。

      もう一方のスレッドがすでに交換ポイントで待機している場合、そのスレッドはスレッドのスケジューリングを再開して、現在のスレッドが渡すオブジェクトを受け取ります。 現在のスレッドはすぐに復帰して、もう一方のスレッドが交換ポイントに渡すオブジェクトを受け取ります。

      交換ポイントで待機中の他のスレッドが存在しない場合、現在のスレッドはスレッドのスケジューリングに関して無効になり、次の2つのいずれかが起きるまで待機します。

      • ほかのスレッドが交換ポイントに入る
      • ほかのスレッドが現在のスレッドに割り込みを行う。

      現在のスレッドで、

      • このメソッドへのエントリ上で設定された割込みステータスが保持されるか、
      • 交換の待機中に割り込みが発生した場合、
      InterruptedExceptionがスローされ、現在のスレッドの割込みステータスがクリアされます。

      パラメータ:
      x - 交換するオブジェクト
      戻り値:
      もう一方のスレッドにより提供されるオブジェクト
      例外:
      InterruptedException - 待機中に現在のスレッドで割込みが発生した場合
    • exchange

      public V exchange(V x, long timeout, TimeUnit unit) throws InterruptedException, TimeoutException
      現在のスレッドは、割り込みが発生するか、指定された待機時間が経過しないかぎり、もう一方のスレッドがこの交換ポイントに達するまで待機し、指定されたオブジェクトをそのスレッドに転送して、代わりにもう一方のスレッドのオブジェクトを受け取ります。

      もう一方のスレッドがすでに交換ポイントで待機している場合、そのスレッドはスレッドのスケジューリングを再開して、現在のスレッドが渡すオブジェクトを受け取ります。 現在のスレッドはすぐに復帰して、もう一方のスレッドが交換ポイントに渡すオブジェクトを受け取ります。

      交換ポイントで待機中の他のスレッドが存在しない場合、現在のスレッドはスレッドのスケジューリングに関して無効になり、次の3つのいずれかが起きるまで待機します。

      • ほかのスレッドが交換ポイントに入る
      • ほかのスレッドが現在のスレッドに割り込みを行う。または
      • 指定された待機時間が経過する。

      現在のスレッドで、

      • このメソッドへのエントリ上で設定された割込みステータスが保持されるか、
      • 交換の待機中に割り込みが発生した場合、
      InterruptedExceptionがスローされ、現在のスレッドの割込みステータスがクリアされます。

      指定された待機時間が経過すると、TimeoutExceptionがスローされます。 時間がゼロまたはそれより小さい場合、メソッドは待機しません。

      パラメータ:
      x - 交換するオブジェクト
      timeout - 待機する最長時間
      unit - timeout引数の時間単位
      戻り値:
      もう一方のスレッドにより提供されるオブジェクト
      例外:
      InterruptedException - 待機中に現在のスレッドで割込みが発生した場合
      TimeoutException - 別のスレッドが交換に入る前に、指定された待機時間が経過した場合