CountDownLatch

让一些线程堵塞直到另一个线程完成一系列操作后才被唤醒。CountDownLatch 主要有两个方法,当一个或多个线程调用 await 方法时,调用线程会被堵塞,其他线程调用 countDown 方法会将计数减一(调用 countDown 方法的线程不会堵塞),当计数其值变为零时,因调用 await 方法被堵塞的线程会被唤醒,继续执行。

假设我们有这么一个场景,教室里有班长和其他6个人在教室上自习,怎么保证班长等其他6个人都走出教室在把教室门给关掉。

public class CountDownLanchDemo {
public static void main(String[] args) {
for (int i = 0; i < 6; i++) {
new Thread(() -> {
System.out.println(Thread.currentThread().getName() + " 离开了教室...");
}, String.valueOf(i)).start();
}
System.out.println("班长把门给关了,离开了教室...");
}
} 0 离开了教室...
1 离开了教室...
2 离开了教室...
3 离开了教室...
班长把门给关了,离开了教室...
5 离开了教室...
4 离开了教室...

发现班长都没有等其他人理他教室就把门给关了,此时我们就可以使用 CountDownLatch 来控制

public class CountDownLanchDemo {
public static void main(String[] args) throws InterruptedException {
CountDownLatch countDownLatch = new CountDownLatch(6);
for (int i = 0; i < 6; i++) {
new Thread(() -> {
countDownLatch.countDown();
System.out.println(Thread.currentThread().getName() + " 离开了教室...");
}, String.valueOf(i)).start();
}
countDownLatch.await();
System.out.println("班长把门给关了,离开了教室...");
}
}
0 离开了教室...
1 离开了教室...
2 离开了教室...
3 离开了教室...
4 离开了教室...
5 离开了教室...
班长把门给关了,离开了教室...
 

使用枚举完成countDownLatch案例

@Setter
@Getter
public class CountDownLatchDemo { public static void main(String[] args) throws InterruptedException { CountDownLatch countDownLatch=new CountDownLatch(6) ; for (int i = 1; i <=6; i++) {
new Thread(()->{
System.out.println(Thread.currentThread().getName()+"国被灭.......");
countDownLatch.countDown();
},CountryEnum.getcountryEnum(i).getName()+"").start();
} countDownLatch.await(); System.out.println(CountryEnum.seven+"国一统华夏");
}
} @Getter
enum CountryEnum {
one(1, "齐", "100", "demaxiya1"),
two(2, "楚", "100", "demaxiya1"),
three(3, "燕", "100", "demaxiya1"),
four(4, "韩", "100", "demaxiya1"),
five(5, "赵", "100", "demaxiya1"),
six(6, "巍", "100", "demaxiya1"),
seven(7, "秦", "100", "demaxiya1");
private Integer id; private String name;
private String time;
private String beizhu; CountryEnum(Integer id, String name, String time, String beizhu) {
this.id = id;
this.name = name;
this.time = time;
this.beizhu = beizhu;
}
public static CountryEnum getcountryEnum(Integer id ){
for (CountryEnum value : values()) {
if (value.id==id){
return value;
}
}
return null;
}
}

打印

齐国被灭.......
燕国被灭.......
楚国被灭.......
韩国被灭.......
巍国被灭.......
赵国被灭.......
seven国一统华夏

 

、CyclicBarrier(集齐七颗龙珠召唤神龙)

  1. CycliBarrier

    可循环(Cyclic)使用的屏障。让一组线程到达一个屏障(也可叫同步点)时被阻塞,知道最后一个线程到达屏障时,屏障才会开门,所有被屏障拦截的线程才会继续干活,线程进入屏障通过CycliBarrier的await()方法

  2. 代码示例:

    import java.util.concurrent.BrokenBarrierException;
    import java.util.concurrent.CyclicBarrier; public class CyclicBarrierDemo {
    public static void main(String[] args) {
    cyclicBarrierTest();
    } public static void cyclicBarrierTest() {
    CyclicBarrier cyclicBarrier = new CyclicBarrier(7, () -> {
    System.out.println("====召唤神龙=====");
    });
    for (int i = 1; i <= 7; i++) {
    final int tempInt = i;
    new Thread(() -> {
    System.out.println(Thread.currentThread().getName() + "\t收集到第" + tempInt + "颗龙珠");
    try {
    cyclicBarrier.await();
    } catch (InterruptedException e) {
    e.printStackTrace();
    } catch (BrokenBarrierException e) {
    e.printStackTrace();
    }
    }, "" + i).start();
    }
    }
    }

    打印

    2 收集到第2颗龙珠
    3 收集到第3颗龙珠
    1 收集到第1颗龙珠
    5 收集到第5颗龙珠
    4 收集到第4颗龙珠
    6 收集到第6颗龙珠
    7 收集到第7颗龙珠
    ====召唤神龙=====

     

    3、Semaphore信号量

    可以代替Synchronize和Lock

    1. 信号量主要用于两个目的,一个是用于多个共享资源的互斥作用,另一个用于并发线程数的控制

    2. 代码示例:

      抢车位示例:

  3. package juc.lock.SemaphoreDemo;
    
    import java.util.concurrent.Semaphore;
    
    /**
    * @Classname SemaphoreDemo
    * @Description TODO
    * @Date 2020/7/13 23:03
    * @Created by imp
    */
    public class SemaphoreDemo { public static void main(String[] args) {
    Semaphore semaphore=new Semaphore(3); //3个车位 for (int i = 0; i < 6; i++) {
    new Thread(()->{
    try {
    //抢占车位
    semaphore.acquire();
    System.out.println(Thread.currentThread().getName()+"\t抢占到车位");
    Thread.sleep(2000);
    System.out.println(Thread.currentThread().getName()+"\t停两秒钟离开");
    } catch (InterruptedException e) {
    e.printStackTrace();
    }finally {
    semaphore.release();
    }
    },String.valueOf(i)).start();
    }
    }
    }

    打印:

    0 抢占到车位
    1 抢占到车位
    4 抢占到车位
    0 停两秒钟离开
    5 抢占到车位
    1 停两秒钟离开
    4 停两秒钟离开
    2 抢占到车位
    3 抢占到车位
    5 停两秒钟离开
    3 停两秒钟离开
    2 停两秒钟离开

     

CountDownLatch/CyclicBarrier/Semaphore 使用过吗的更多相关文章

  1. 并发包下常见的同步工具类详解(CountDownLatch,CyclicBarrier,Semaphore)

    目录 1. 前言 2. 闭锁CountDownLatch 2.1 CountDownLatch功能简介 2.2 使用CountDownLatch 2.3 CountDownLatch原理浅析 3.循环 ...

  2. CountDownLatch/CyclicBarrier/Semaphore 使用过吗?

    CountDownLatch/CyclicBarrier/Semaphore 使用过吗?下面详细介绍用法: 一,(等待多线程完成的)CountDownLatch  背景; countDownLatch ...

  3. Java并发编程工具类 CountDownLatch CyclicBarrier Semaphore使用Demo

    Java并发编程工具类 CountDownLatch CyclicBarrier Semaphore使用Demo CountDownLatch countDownLatch这个类使一个线程等待其他线程 ...

  4. 并发包下常见的同步工具类(CountDownLatch,CyclicBarrier,Semaphore)

    在实际开发中,碰上CPU密集且执行时间非常耗时的任务,通常我们会选择将该任务进行分割,以多线程方式同时执行若干个子任务,等这些子任务都执行完后再将所得的结果进行合并.这正是著名的map-reduce思 ...

  5. Java中的4个并发工具类 CountDownLatch CyclicBarrier Semaphore Exchanger

    在 java.util.concurrent 包中提供了 4 个有用的并发工具类 CountDownLatch 允许一个或多个线程等待其他线程完成操作,课题点 Thread 类的 join() 方法 ...

  6. 高并发第十单:J.U.C AQS(AbstractQueuedSynchronizer) 组件:CountDownLatch. CyclicBarrier .Semaphore

    这里有一篇介绍AQS的文章 非常好: Java并发之AQS详解 AQS全名:AbstractQueuedSynchronizer,是并发容器J.U.C(java.lang.concurrent)下lo ...

  7. CountDownLatch CyclicBarrier Semaphore 比较

    document CountDownLatch A synchronization aid that allows one or more threads to wait until a set of ...

  8. 多线程中 CountDownLatch CyclicBarrier Semaphore的使用

    CountDownLatch 调用await()方法的线程会被挂起,它会等待直到count值为0才继续执行.也可以传入时间,表示时间到之后,count还没有为0的时候,就会继续执行. package ...

  9. 等待某(N)个线程执行完再执行某个线程的几种方法(Thread.join(),CountDownLatch,CyclicBarrier,Semaphore)

    1.main线程中先调用threadA.join() ,再调用threadB.join()实现A->B->main线程的执行顺序 调用threadA.join()时,main线程会挂起,等 ...

  10. 并发工具类的使用 CountDownLatch,CyclicBarrier,Semaphore,Exchanger

    1.CountDownLatch 允许一个或多个线程等待直到在其他线程中执行的一组操作完成的同步辅助. A CountDownLatch用给定的计数初始化. await方法阻塞,直到由于countDo ...

随机推荐

  1. fabric智能合约模板

    以创建用户为例,我觉得基本都是这个框架,用特殊功能直接再往上加,欢迎留言交流 func createUser(stub shim.ChaincodeStubInterface, args []stri ...

  2. uni-app中封装统一请求函数

    封装统一请求函数有利于项目的维护 整体功能简单实用,但小编遇到一个巨坑,项目中在vue文件使用跳转方法,url参数输入 "/" 后工具提示的路径为 "/pages/log ...

  3. SpringBoot + Mybatis-Plus 实现多数据源简单示例

    1. 简介   在单体项目中,经常出现想要访问多个数据源的情况,或者因为某些性能瓶颈,将大数据量的业务表分离到另一个库等情况.   实现多数据源的方案有很多,Mybatis-Plus提供了非常简单的实 ...

  4. 【C#】DockPanelSuite 中 DockState.Document 状态下子窗体控件不显示的解决方案

    DockPanelSuite 是 Winform 中优秀的布局控件,但是这次使用过程中却出了个问题. 我遇到的问题是这样的,主窗体是通过 ShowDialog 显示的,子窗体的停靠状态为 DockSt ...

  5. com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: Specified key was too long; max key length is 767 bytes

    hive 安装完成后创建表的时候出现错误 NestedThrowablesStackTrace:com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorExce ...

  6. Java中中文排序器

    在Java中使用Collator类按照汉字拼音排序字符串 public static void main(String[] args) throws Exception{ String[] strs ...

  7. 在IDEA中使用JDBC获取数据库连接时的报错及解决办法

    在IDEA中使用JDBC获取数据库连接时,有时会报错Sat Dec 19 19:32:18 CST 2020 WARN: Establishing SSL connection without ser ...

  8. js深克隆与浅克隆

    定义: 浅克隆: 克隆对象的一层属性, 如果对象还有对象的话,里面的对象没有进行克隆,只是把地址给了别人.也可以理解为只是简单的克隆了躯体,但是没有得到其灵魂: 深克隆:克隆对象的多层属性,对象里面还 ...

  9. C# 托管与非托管类型 堆和栈 值类型与引用类型 装箱与拆箱

    一.托管类型与非托管类型 1.托管类型 托管类型包括 引用类型 以及 包含有引用类型或托管类型成员的结构. 引用类型 含引用类型或托管类型成员(字段.自动实现 get 访问器的属性)的结构 // 托管 ...

  10. 使用xshell软件进行文件的上传和下载

    1.选择xshell的文件里面的属性-->文件传输,把上传路径和下载路径设置好. 上传路径:介绍我们需要向Linux系统里面传东西. 下载路径:就是我们把Linux系统里面的大小拷贝出来. 2. ...