【Java】10.CyclicBarrier使用与分析

来源:互联网 发布:淘宝美工负责什么工作 编辑:程序博客网 时间:2024/05/21 06:25
1.官方资料:

The java.util.concurrent.CyclicBarrier class is a synchronization mechanism that can synchronize threads progressing through some algorithm. In other words, it is a barrier that all threads must wait at, until all threads reach it, before any of the threads can continue. Here is a diagram illustrating that: image

The threads wait for each other by calling the await() method on the CyclicBarrier. Once N threads are waiting at the CyclicBarrier, all threads are released and can continue running.

Creating a CyclicBarrier

When you create a CyclicBarrier you specify how many threads are to wait at it, before releasing them. Here is how you create a CyclicBarrier:

CyclicBarrier barrier = new CyclicBarrier(2);
Waiting at a CyclicBarrier

Here is how a thread waits at a CyclicBarrier:

barrier.await();
2.示例:
package com.naton.manager.concurrent.cyclic;import java.util.concurrent.BrokenBarrierException;import java.util.concurrent.CyclicBarrier;public class CyclicBarrierTest {public static void main(String[] args) {Runnable barrier1Action = new Runnable() {    public void run() {        System.out.println("BarrierAction 1 executed ");    }};Runnable barrier2Action = new Runnable() {    public void run() {        System.out.println("BarrierAction 2 executed ");    }};CyclicBarrier barrier1 = new CyclicBarrier(2, barrier1Action);CyclicBarrier barrier2 = new CyclicBarrier(2, barrier2Action);CyclicBarrierRunnable barrierRunnable1 =        new CyclicBarrierRunnable(barrier1, barrier2);CyclicBarrierRunnable barrierRunnable2 =new CyclicBarrierRunnable(barrier1, barrier2);new Thread(barrierRunnable1).start();new Thread(barrierRunnable2).start();}static class CyclicBarrierRunnable implements Runnable{    CyclicBarrier barrier1 = null;    CyclicBarrier barrier2 = null;    public CyclicBarrierRunnable(            CyclicBarrier barrier1,            CyclicBarrier barrier2) {        this.barrier1 = barrier1;        this.barrier2 = barrier2;    }    public void run() {        try {            Thread.sleep(1000);            System.out.println(Thread.currentThread().getName() +                                " waiting at barrier 1");            this.barrier1.await();            Thread.sleep(1000);            System.out.println(Thread.currentThread().getName() +                                " waiting at barrier 2");            this.barrier2.await();            System.out.println(Thread.currentThread().getName() +                                " done!");        } catch (InterruptedException e) {            e.printStackTrace();        } catch (BrokenBarrierException e) {            e.printStackTrace();        }    }}}输出:Thread-0 waiting at barrier 1Thread-1 waiting at barrier 1BarrierAction 1 executedThread-1 waiting at barrier 2Thread-0 waiting at barrier 2BarrierAction 2 executedThread-0 done!Thread-1 done!
3.使用场景:

需要所有的子任务都完成时,才执行主任务,这个时候就可以选择使用CyclicBarrier。

示例:

public class CyclicBarrierTest {        public static void main(String[] args) throws IOException, InterruptedException {          //如果将参数改为4,但是下面只加入了3个选手,这永远等待下去          //Waits until all parties have invoked await on this barrier.           CyclicBarrier barrier = new CyclicBarrier(3);            ExecutorService executor = Executors.newFixedThreadPool(3);          executor.submit(new Thread(new Runner(barrier, "1号选手")));          executor.submit(new Thread(new Runner(barrier, "2号选手")));          executor.submit(new Thread(new Runner(barrier, "3号选手")));            executor.shutdown();      }  }    class Runner implements Runnable {      // 一个同步辅助类,它允许一组线程互相等待,直到到达某个公共屏障点 (common barrier point)      private CyclicBarrier barrier;        private String name;        public Runner(CyclicBarrier barrier, String name) {          super();          this.barrier = barrier;          this.name = name;      }        @Override      public void run() {          try {              Thread.sleep(1000 * (new Random()).nextInt(8));              System.out.println(name + " 准备好了...");              // barrier的await方法,在所有参与者都已经在此 barrier 上调用 await 方法之前,将一直等待。              barrier.await();          } catch (InterruptedException e) {              e.printStackTrace();          } catch (BrokenBarrierException e) {              e.printStackTrace();          }          System.out.println(name + " 起跑!");      }  }
原创粉丝点击