当前位置: 代码迷 >> 综合 >> Java 并发工具类之 CyclicBarrier
  详细解决方案

Java 并发工具类之 CyclicBarrier

热度:25   发布时间:2023-12-26 12:54:07.0

CyclicBarrier ,可循环(计数器可以重置)利用的同步屏障,线程到达一个屏障会阻塞,到达屏障的线程数达到设置的值时,所有被屏障阻塞的线程开始执行。

1. 概述 

构造函数:public CyclicBarrier(int parties),设置初始值。

public CyclicBarrier(int parties, Runnable barrierAction),优先执行 barrierAction。

设置屏障方法:public int await()

有时间限制的设置屏障方法,超时则不再阻塞:public int await(long timeout, TimeUnit unit)

屏障是否损坏:阻塞的线程被中断(超时也会损坏屏障),就损坏了,损坏返回true:public boolean isBroken()

重置计数器:public void reset()。

当前等待的数量:public int getNumberWaiting()

2. 测试代码

设置初始值为2 。

package util;import java.util.concurrent.BrokenBarrierException;
import java.util.concurrent.CyclicBarrier;public class CyclicBarrierStudy implements Runnable{static CyclicBarrier cyclicBarrier = new CyclicBarrier(2);public static void main(String[] args) throws BrokenBarrierException, InterruptedException {new Thread(new CyclicBarrierStudy()).start();cyclicBarrier.await();System.out.println(2);}@Overridepublic void run() {try {cyclicBarrier.await();} catch (InterruptedException e) {e.printStackTrace();} catch (BrokenBarrierException e) {e.printStackTrace();}System.out.println(1);}
}

运行截图如下,屏障处的线程执行顺序不定。

设置初始值为3(其他代码不变)。

static CyclicBarrier cyclicBarrier = new CyclicBarrier(3);

发生阻塞,因为到达屏障的线程数需要达到设置的值3,如下图所示。 

有时间限制的设置屏障方法,超时则不再阻塞:public int await(long timeout, TimeUnit unit)。

屏障是否损坏,阻塞的线程被中断(超时也会损坏屏障),就损坏了,损坏返回true:public boolean isBroken()。

package util;import java.util.concurrent.BrokenBarrierException;
import java.util.concurrent.CyclicBarrier;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException;public class CyclicBarrierStudy implements Runnable{static CyclicBarrier cyclicBarrier = new CyclicBarrier(3);public static void main(String[] args) throws BrokenBarrierException, InterruptedException {new Thread(new CyclicBarrierStudy()).start();try {cyclicBarrier.await(1000, TimeUnit.MILLISECONDS);} catch (TimeoutException e) {e.printStackTrace();}System.out.println("step1 " + cyclicBarrier.isBroken());}@Overridepublic void run() {try {try {cyclicBarrier.await(1000, TimeUnit.MILLISECONDS);} catch (TimeoutException e) {e.printStackTrace();}} catch (InterruptedException e) {e.printStackTrace();} catch (BrokenBarrierException e) {e.printStackTrace();}System.out.println("step2 " + cyclicBarrier.isBroken());}
}

运行截图,超时等待(不再阻塞),屏障破坏。

参考文献:

  • Java并发编程的艺术 / 方腾飞,魏鹏,魏晓明著 .  ——北京:机械工业出版社,2015.7
  相关解决方案