AたCountDownLatch(ブロッキング)、セマフォ(セマフォ)、CyclicBarrierを

A、CountDowmLatch(ラッチ)(ダウンカウンタラッチ)

  下に位置たCountDownLatchクラスjava.util.concurrentパッケージは、特定の操作が完了すると、操作の唯一の他の全てのスレッドが終了し、現在の運転を継続しなければなりません。

  同様のカウンタ機能を実現するために使用します。他に実行するために4つのタスクの完了後に実行するために例えば、タスクAがあり、それは、あなたがこの機能を実装するためにされたCountDownLatchを使用することができ、待機します。

1  ファイナル AたCountDownLatch LATCH = 新しい新たCountDownLatch(2 );
 2  新しい新しいスレッド(){
 3      公共 ボイドRUN(){
 。4          。のSystem.out.println( "子スレッド" +にThread.currentThread()のgetName() + "が実行されています" 。5          のThread.sleep(3000 。6          のSystem.out.println( "子スレッド" +にThread.currentThread()のgetName() + " 終了しました。" 。7          latch.countDown();
 8      };
 9  } .start();
 10  新しい新しいスレッド(){ 
 11      公共 ボイドRUN(){
 12であります         System.out.println( "子スレッド" +にThread.currentThread()のgetName() + " 実行" );
 13である          のThread.sleep(3000 );
 14          のSystem.out.println( "子スレッド" +にThread.currentThread ().getName()+ "完成" );
 15          latch.countDown();
 16      };
 17  } .start();
 18であるのSystem.out.println( "スレッドを待って完成サブ2 ...です" )。
 。19  )(latch.await;
 20であるのSystem.out.println( "スレッドが終了し、サブ2を有している" );
 21であるのSystem.out.println( "続行するメインスレッド" );
 22 }

二つ、セマフォ(セマフォ - 同時にアクセススレッドの数を制御)

  セマフォは、同時にアクセスするスレッドの数を制御待機しない場合、)(取得してライセンスを取得しますが、ライセンスが解放によって解放されることができます()。

いくつかの方法で、より重要なセマフォクラス:

  1)公共無効取得():ライセンスが取得できない場合は、ライセンスを取得するために使用されるが、それはその許可を知って、待機する必要があります。

  2)公共無効取得(int型の許可):許可ライセンスを取得。

  3)公共のボイドリリース(){}:無料ライセンス、注意、ライセンスをリリースする前に、ライセンスを取得する必要があります。

  4)公共ボイド放出(INT許可){}:許可ライセンスを解放します。

上記の4つの方法は、あなたがすぐに結果を取得したい場合は、次のいくつかのメソッドを使用することができ、ブロックされます。

  1)公共ブールtryAcquire():、ライセンスを取得しようとする買収が成功すれば、その後すぐに買収が失敗した場合、それはすぐにfalseを返し、trueを返します。

  2)公共ブールtryAcquire(長いタイムアウト、TimeUnitで単位):ライセンスを取得しようとする試みは、指定された時間内に成功した場合、直ちにそれ以外の場合は、すぐに偽を返し、trueを返します。

  3)公共ブールtryAcquire(int型の許可を):取得に失敗した場合に許可のライセンスを取得しようと、買収が成功すれば、その後すぐにtrueを返します、それはすぐにfalseを返します。

  4)公共ブールtryAcquire(int型の許可、長いタイムアウト、TimeUnitで単位):指定された時間内に成功した場合、その後すぐにtrueを返し、許可のライセンスを取得しようとする試みは、それ以外の場合は、すぐにfalseを返します。

  5)またavailablePermitsによって使用可能なライセンスの数を取得する()メソッドであってもよいです。

  例:工場出荷時は、同時に5台のマシン、一台のマシンを持っているだけで、作業者が使用することができた場合は、単に他の労働者が継続して、走りました。その後、我々はセマフォによって行うことができます。

 1 int N = 8; //工人数
 2 Semaphore semaphore = new Semaphore(5); //机器数目
 3 for(int i=0;i<N;i++){
 4     new Worker(i,semaphore).start();
 5 }
 6 static class Worker extends Thread{
 7     private int num;
 8     private Semaphore semaphore;
 9     public Worker(int num,Semaphore semaphore){
10         this.num = num;
11         this.semaphore = semaphore;
12     }
13     public void run() {
14         try {
15             semaphore.acquire();
16             System.out.println("工人"+this.num+"占用一个机器在生产...");
17             Thread.sleep(2000);
18             System.out.println("工人"+this.num+"释放出机器");
19             semaphore.release();
20         } catch (InterruptedException e) {
21             e.printStackTrace();
22         }
23     }
24 }

三、CyclicBarrier(回环栅栏-等待至barrier状态再全部同时执行)

  回环栅栏,通过它可以实现让一组线程等待至某个状态之后再全部同时执行,叫做回环,是因为当所有等待线程都被释放以后,CyclicBarrier可以被重用。我们暂且把这种状态叫做barrier,当调用await()方法之后,线程就处于barrier了。

  CyclicBarrier中最重要的方法就是await方法,它有两个重载版本:

    1)public int await():用来挂起当前线程,直至所有线程都到达barrier状态再同时执行后续任务。

    2)public int await(long timeout,TimeUnit unit):让这些线程等待至一定的时间,如果还有线程没有到达barrier状态就直接让到达barrier的线程执行后续任务。

  具体使用如下:

 1  public static void main(String[] args) {
 2      int N = 4;
 3      CyclicBarrier barrier = new CyclicBarrier(N);
 4      for(int i=0;i<N;i++)
 5          new Writer(barrier).start();
 6      }
 7  static class Writer extends Thread{
 8      private CyclicBarrier cyclicBarrier;
 9      public Writer(CyclicBarrier cyclicBarrier) {
10          this.cyclicBarrier = cyclicBarrier;
11      }
12  public void run() {
13      try {
14          Thread.sleep(5000); //以睡眠来模拟线程需要预定写入数据操作
15 System.out.println("线程"+Thread.currentThread().getName()+"写入数据完毕,等待其他线程写入完毕");
16          cyclicBarrier.await();
17      } catch (InterruptedException e) {
18          e.printStackTrace();
19      }catch(BrokenBarrierException e){
20          e.printStackTrace();
21      }
22      System.out.println("所有线程写入完毕,继续处理其他任务,比如数据操作");
23      }
24  }

 

三者之间的联系与区别:

  CountDownLatch和CyclicBarrier都能够实现线程之间的等待,只不过它们侧重点不同。CountDownLatch一般用于某个线程A等待若干个线程执行完任务之后,它才执行;而CyclicBarrier一般用于一组线程互相等待至某个状态,然后这一组线程再同时执行。另外,CountDownLatch是不能够重用的,而CyclicBarrier是可以重用的。

  Semaphore其实和锁有点类似,它一般用于控制对某组资源的访问权限。

おすすめ

転載: www.cnblogs.com/HuiH/p/11904898.html