欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

concurrent之初识CyclicBarrier和实践案例

程序员文章站 2022-05-04 21:40:06
...

介绍:

CyclicBarrier:循环栅栏  (个人理解:多线程完成任务后汇报情况的地方

cycilc:循环的意思

barrier:障碍

描述CyclicBarrier的栗子:

生活中我们会约朋友们到某个餐厅一起吃饭,有些朋友可能会早到,有些朋友可能会晚到,但是这个餐厅规定必须
等到所有人到齐之后才会让我们进去。这里的朋友们就是各个线程,餐厅就是 CyclicBarrier。

构造方法:

public CyclicBarrier(int parties);
//parties 等待的线程数,barrierAction 最后的线程要做的任务
public CyclicBarrier(int parties, Runnable barrierAction);

方法:

public int await() throws InterruptedException, BrokenBarrierException
public int await(long timeout, TimeUnit unit) throws InterruptedException, 
BrokenBarrierException, TimeoutException

 

CyclicBarrier常见的两个异常:

InterruptedException和BrokenBarrierException

InterruptedException:当前处于线程等待的过程被中断而抛出的异常。

BrokenBarrierException:需要集合的线程有一个线程被中断就会导致线程永远都无法集齐, 导致“栅栏损坏”,剩下的线程就会抛出BrokenBarrierException异常

 

实践

CyclicBarrier之吃饭案例,也可用于计算等待:

package com.demo;

import java.util.concurrent.BrokenBarrierException;
import java.util.concurrent.CyclicBarrier;
import java.util.concurrent.TimeUnit;

/**
 * @Description
 * @Author by mocar小师兄
 * @Date 2020/3/12 16:41
 **/
public class CyclicBarrierTest {
    private static final int Num=Runtime.getRuntime().availableProcessors();
    private static Boolean Flag;
    private static class TaskThread implements Runnable{
        private CyclicBarrier cyclicBarrier;

        public TaskThread(CyclicBarrier _cyclicBarrier) {
            this.cyclicBarrier = _cyclicBarrier;
        }

        @Override
        public void run() {
            try {
                System.out.println(Thread.currentThread().getName() + "\t 已经到餐厅门口");
                cyclicBarrier.await();
                doSomething();
                cyclicBarrier.await();
            } catch (InterruptedException e) {
                e.printStackTrace();
            } catch (BrokenBarrierException e) {
                e.printStackTrace();
            }
        }

        private void doSomething(){
            try {
                TimeUnit.SECONDS.sleep(2);
                System.out.println(Thread.currentThread().getName() + "\t开始吃饭");
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }
    private static class BarrierTask implements Runnable{
        @Override
        public void run() {
            if (Flag){
                System.out.println(Num + "\t个朋友都吃完饭了");
            }else {
                System.out.println(Num + "\t个朋友都到期餐厅门口了");
                Flag=true;
            }
        }
    }

    public static void main(String[] args) {
        CyclicBarrier _cyclicBarrier = new CyclicBarrier(Num, new BarrierTask());
        Thread[] threads =new Thread[Num];
        Flag=false;
        for (int i = 0; i <Num ; i++) {
            threads[i] = new Thread(new TaskThread(_cyclicBarrier),"朋友" + (i+1));
            threads[i].start();
        }

    }
}

结果显示:

当所有子线程集合完毕,开始执行BarrierTask任务类

concurrent之初识CyclicBarrier和实践案例

 

参考:

https://www.jianshu.com/p/333fd8faa56e

相关标签: concurrent