倒计数锁存器(CountDown Latch)和 CyclicBarrier(同步屏障)

倒计数锁存器(CountDown Latch)是异常性障碍,允许一个或多个线程等待一个或者多个其他线程来做某些事情。

 public  static long time(Executor executor,int concurrency,final Runnable action)throws InterruptedException{
        //CountDownLatch 构造器参数代表 只有调用countDown()方法达到这个int值的时候,才能继续(所以多线程的情况下可以在此阻塞)
        final CountDownLatch ready=new CountDownLatch(concurrency);
        final CountDownLatch start=new CountDownLatch(1);
        final CountDownLatch done=new CountDownLatch(concurrency);
        for (int i=0;i<concurrency;i++){
            executor.execute(new Runnable() {
                @Override
                public void run() {
                    ready.countDown();//准备好了一个就++1
                    try{
                        start.await();//等待所有for循环跑完 主线程执行countDown的时候才能继续走
                        action.run();
                    }catch (InterruptedException ex){
                        Thread.currentThread().interrupt();
                    }finally{
                        done.countDown();//线程执行完了才能++
                    }
                }
            });
        }
        ready.await();
        long startNanos=System.nanoTime();
        start.countDown();
        done.await();//阻塞等待异步线程的countDown()调用次数达到阀值
        return  System.nanoTime()-startNanos;
    }

对于间歇式的定时,始终应该优先使用System.nanoTime()而不是System.currentTimeMills,前者更加准确更加精确并且不受系统的实时时钟的调整影响。

三个CountdownLatch也可以用CyclicBarrier(同步屏障)代替。

 public static long time1(Executor executor, int concurrency, final Runnable action) {
        CyclicBarrier cyclicBarrier = new CyclicBarrier(concurrency);
        long startNanos = System.nanoTime();
        for (int i = 0; i < concurrency; i++) {
            executor.execute(new Runnable() {
                @Override
                public void run() {
                    try {
                        action.run();
                    } finally {
                        try {
                            cyclicBarrier.await();
                        } catch (BrokenBarrierException ex) {

                        } catch (InterruptedException ex) {

                        }
                    }
                }
            });
        }
        return System.nanoTime() - startNanos;
    }

CountDownLatch的计数器只能使用一次。而CyclicBarrier的计数器可以使用reset() 方法重置。所以CyclicBarrier能处理更为复杂的业务场景,比如如果计算发生错误,可以重置计数器,并让线程们重新执行一次。
CyclicBarrier还提供其他有用的方法,比如getNumberWaiting方法可以获得CyclicBarrier阻塞的线程数量。isBroken方法用来知道阻塞的线程是否被中断。

总的来说就是可以同步等待所有异步任务完成后进行汇总操作。

原文地址:https://www.cnblogs.com/ylsforever/p/8434863.html

时间: 2024-08-02 22:44:52

倒计数锁存器(CountDown Latch)和 CyclicBarrier(同步屏障)的相关文章

java CyclicBarrier同步屏障

CyclicBarrier的字面意思是可循环使用的屏障,它的主要作用是,让一组线程到达一个屏障时被阻塞,知道最后一个线程到达屏障时,屏障才会打开,所有被屏障拦截的线程才会继续运行. 1.简介: CyclicBarrier默认的构造方法是CyclicBarrier(int parties),其中参数标识屏障拦截的线程数量,每个线程调用await方法告诉CyclicBarrier我已经到达了屏障,然后当前线程被阻塞. package com.test; import java.util.concur

线程:CyclicBarrier同步工具类

一个同步辅助类,它允许一组线程互相等待,直到到达某个公共屏障点.比如公司组织活动出去玩,需要在公司门口一起搭车去.每个人从家里出发去公司门口,到达的时间肯定先后不一样,所以公司的车要一直等待,等所有人到齐后,才开车出发.CyclicBarrier就类似这样的功能,当所有线程到达"屏蔽点"的时候,才往下走. 具体等待多少根线程到达,可以在构造方法里指定CyclicBarrier(int parties). 当你的parties设为3的时候,假设只有2根线程到达此处,那程序会一直在此等待.

jQuery超酷3D翻牌式倒计数特效

这是一款效果非常炫酷的jQuery和CSS3 3D翻牌式倒计数特效.这个特效就像NBA比赛的记分牌一样,可以像翻牌一样上下翻动当前的记分牌.该特效将牌子从水平中心线分成两半,上下两半可以绕中心线做翻转动画,效果非常神奇. 效果演示:http://www.htmleaf.com/Demo/201503291592.html 下载地址:http://www.htmleaf.com/jQuery/Layout-Interface/201503291591.html

concurrent(四)同步屏障 CyclicBarrier &amp; 源码分析

参考文档:Java多线程系列--"JUC锁"10之 CyclicBarrier原理和示例:https://www.cnblogs.com/skywang12345/p/3533995.html简介CyclicBarrier是一个同步辅助类,允许一组线程互相等待,直到到达某个公共屏障点 (common barrier point).因为该 barrier 在释放等待线程后可以重用,所以称它为循环的 barrier.基于ReentrantLock实现举个栗子 /** * 简单模拟一下对战平

高级同步器:可重用的同步屏障Phaser

引自:https://shift-alt-ctrl.iteye.com/blog/2302923 在JAVA 1.7引入了一个新的并发API:Phaser,一个可重用的同步barrier.在此前,JAVA已经有CyclicBarrier.CountDownLatch这两种同步barrier,但是Phaser更加灵活,而且侧重于“重用”. 一.简述 1.注册机制:与其他barrier不同的是,Phaser中的“注册的同步者(parties)”会随时间而变化,Phaser可以通过构造器初始化part

多线程之倒计时器CountDownLatch和循环栅栏CyclicBarrier

1.倒计时器CountDownLatch CountDownLatch是一个多线程控制工具类.通常用来控制线程等待,它可以让一个线程一直等待知道计时结束才开始执行 构造函数: public CountDownLatch(int count) //count 计数个数 例如:在主线程中启动10个子线程去数据库中获取分页数据,需要等到所有线程数据都返回之后统一做统计处理 public class CountDownLatchDemo implements Runnable{ private stat

并发工具类(二)同步屏障CyclicBarrier

前言 ??JDK中为了处理线程之间的同步问题,除了提供锁机制之外,还提供了几个非常有用的并发工具类:CountDownLatch.CyclicBarrier.Semphore.Exchanger.Phaser: ??CountDownLatch.CyclicBarrier.Semphore.Phaser 这四个工具类提供一种并发流程的控制手段:而Exchanger工具类则提供了在线程之间交换数据的一种手段. 简介 ??CyclicBarrier 的字面意思是可循环使用(Cyclic)的屏障(Ba

【Java多线程】CyclicBarrier同步辅助类

CyclicBarrier是java.util.concurrent包下的一个同步辅助类,类似于CountDownLatch,也是一个同步计数器. 与CountDownLatch不同的区别是:    CountDownLatch的await()方法阻塞的原因是等待调用一定次数的countDown()方法, 可以在同一线程完成; CyclicBarrier的await()方法阻塞的原因是等待一定数量的线程调用await()方法, 必须在不同线程调用 所以,概括来说: CountDownLatch是

JAVA线程同步辅助类CyclicBarrier循环屏障

CyclicBarrier是一个同步辅助类,主要作用是让一组线程互相等待,知道都到达一个公共障点,在一起走.在涉及一组固定大小的线程的程序中,这些线程必须不时地互相等待,此时 CyclicBarrier 很有用.因为该 barrier 在释放等待线程后可以重用,所以称它为循环 的 barrier. CyclicBarrier 支持一个可选的 Runnable 命令,在一组线程中的最后一个线程到达之后(但在释放所有线程之前),该命令只在每个屏障点运行一次.若在继续所有参与线程之前更新共享状态,此屏