多线程学习(二)CountDownLunch与CyclicBarrier

两个看上去有点像的类,都在java.util.concurrent下,都可以用来表示代码运行到某个点上,二者的区别在于:

(1)CyclicBarrier的某个线程运行到某个点上之后,该线程即停止运行,直到所有的线程都到达了这个点,所有线程才重新运行;CountDownLatch则不是,某线程运行到某个点上之后,只是给某个数值-1而已,该线程继续运行

(2)CyclicBarrier只能唤起一个任务,CountDownLatch可以唤起多个任务

(3)CyclicBarrier可重用,CountDownLatch不可重用,计数值为0该CountDownLatch就不可再用了

CyclicBarrier

public class CyclicBarrierTest {
    /**
     * 工作线程
     */
    private static class Work implements Runnable{
        private CyclicBarrier cyclicBarrier ;

        public Work(CyclicBarrier cyclicBarrier) {
            this.cyclicBarrier = cyclicBarrier;
        }
        //只有所有人都完成第一阶段才能开始第二阶段
        public void run() {

            firstwork();
            try {
                //等待完成第一阶段工作
                cyclicBarrier.await();
                secondWork();
                //完成第二阶段工作
                cyclicBarrier.await();
            } catch (InterruptedException e) {
                e.printStackTrace();
            } catch (BrokenBarrierException e) {
                e.printStackTrace();
            }
        }
        //work1
        private void firstwork(){
            System.out.println(Thread.currentThread().getName()+"完成第一项工作");
        }
        //work2
        private void secondWork(){
            System.out.println(Thread.currentThread().getName()+"完成第二阶段");
        }
    };

    //通知线程
    private static class NoticeThread implements Runnable{
        boolean [] flag = new boolean[2] ;
        public void run() {
            if (!flag[0]){
                System.out.println("通知:第一阶段完成");
                flag[0] = true;
            }else
            if( !flag[1]){
                System.out.println("通知:第二阶段完成");
            }
        }
    }
    public static void main(String[] args) {
        CyclicBarrier cyclicBarrier = new CyclicBarrier(10,new NoticeThread());
        for (int i =0 ;i<10 ;i++){
            new Thread(new Work(cyclicBarrier)).start();
        }
    }
}

结果

Thread-0完成第一项工作
Thread-2完成第一项工作
Thread-1完成第一项工作
Thread-4完成第一项工作
Thread-3完成第一项工作
Thread-7完成第一项工作
Thread-8完成第一项工作
Thread-6完成第一项工作
Thread-5完成第一项工作
Thread-9完成第一项工作
通知:第一阶段完成
Thread-9完成第二阶段
Thread-0完成第二阶段
Thread-2完成第二阶段
Thread-1完成第二阶段
Thread-4完成第二阶段
Thread-3完成第二阶段
Thread-7完成第二阶段
Thread-8完成第二阶段
Thread-6完成第二阶段
Thread-5完成第二阶段
通知:第二阶段完成

从结果看到 cyclicBarrier 阻塞所有线程, 之后 都到达后 ,会唤醒一个通知线程, 之后所有阻塞的工作线程继续执行, 都到达第二阶段 之后唤醒 通知线程,再继续. 并且一个 cyclicBarrier可以重复利用.

CountDownLunch

public class CountDownLunchTest {
    private CountDownLatch countDownLatch  = new CountDownLatch(5);

    public void doWork(){
        countDownLatch.countDown();
        System.out.println(countDownLatch.getCount());
    }

    public static void main(String[] args) throws InterruptedException {
        final CountDownLunchTest test = new CountDownLunchTest();
        Runnable runnable = new Runnable() {
            public void run() {
                test.doWork();
            }
        };
        for (int i = 0; i <5; i++) {
            new Thread(runnable).start();
        }
        test.countDownLatch.await();
        System.out.println("end");
    }
}

其他参考:https://github.com/wowdouble/wowdouble/tree/master/threaddemo

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值