多线程-闭锁CountDownLatch
2024-08-25 20:14:03
闭锁相当于相当于一扇门,在闭锁到达结束状态之前,这扇门一直是关着的,所有的线程都不可以通过。它可以使一个或者一组线程等待某个时间发生。闭锁状态包括一个计数器,初始化的时候传入一个正数,这个数字表示等待的事件的个数。countDown方法递减计数器,表示一个事件已经发生。如果计数器的值为非0,await方法会一直阻塞到计数器为0。当计数器为0,表示等待的事件已经发生,这时候所有的线程才可以继续往下执行。
闭锁的实现有CountDownLatch,类似于我们生活的田径比赛,当运动员听到裁判员的哨声时,运动员才可以开始跑,未听到裁判的哨声运动员不可以跑。这个时候不管所有的运动员是否已经准备就绪了,只要哨声一响,就可以跑。这个跟后面的栅栏有区别,运动员只等待一个事件,就是听到裁判员的哨声响起。下面看一下实现的代码,如下:
package countDownLatch.countDownLatch; import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors; public class CountDownLatchDemo { public static void main(String[]args) throws InterruptedException{
final CountDownLatch startGate=new CountDownLatch(1);
final CountDownLatch endGate=new CountDownLatch(5);
//线程池
ExecutorService exce=Executors.newCachedThreadPool();
//创建5个线程
for(int i=1;i<=5;i++){
final int num=i;
Thread thread =new Thread(new Runnable() {
public void run() {
try {
System.out.println(num+"号选手准备就绪,等待裁判员哨声响起..");
//相当于同步锁Synchronized中的await()方法
startGate.await();
try {
Thread.sleep((long) (Math.random()*10000));
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(num+"号选手到达终点..");
} catch (InterruptedException e) {
e.printStackTrace();
}
finally{
//相当于同步锁Synchronized中的notify()方法,区别在于countDown需要执行5次后才能唤醒await()
endGate.countDown();
}
}
});
exce.execute(thread);
}
long start=System.nanoTime();
System.out.println("裁判员哨声响起..");
Thread.sleep(10000);
//唤醒执行startGate.await()的线程,让线程往下执行
startGate.countDown();
//等待被唤醒,主程序才能继续往下执行,线程中每次执行endGate.countDown()就减1,当为零的时候,主程序往下执行
endGate.await();
long end=System.nanoTime();
System.out.println("所有运动员到达终点,耗时:"+(end-start));
//关闭线程池
exce.shutdown();
}
}
执行结果如下:
参考地址:JAVA并发编程实战
http://m.jb51.net/article/63973.htm
最新文章
- HTML学习笔记——列表和table
- Java图片处理(一)图片合成
- [转]Android中内存占用的含义:(VSS,PSS,RSS,USS)
- RMI学习
- Android 4.1.1源码编译
- javascript中错误使用var造成undefined
- Hello World 老调重谈
- @RISK
- 前端技术之_CSS详解第一天
- 【Python实践-5】使用迭代查找一个list中最小和最大值
- 定时任务框架Quartz-(一)Quartz入门与Demo搭建
- RHEL,红帽CentOS7linux进入单用户(紧急救援)模式修改密码
- 报错:keep must be either ";first";, ";last"; or False
- linux vi如何保存编辑的文件
- mybatis主键的生成
- Android Context类
- Neo4j 文档
- EasyUI写的登录界面
- Ubuntu 搭建etcd
- python标准库介绍——12 time 模块详解
热门文章
- because it violates the following Content Security Policy directive: ";default-src &#39;self&#39; data: gap: https://ssl.gstatic.com &#39;unsafe-eval&#39;";. Note that &#39;script-src&#39; was not explicitly set, so &#39;default-s
- iOS设置导航栏透明度
- 170223、Tomcat部署时war和war exploded区别以及平时踩得坑
- 用RSS订阅微信公众号
- python中获取字典的key列表和value列表
- 11.css定义下拉菜单
- 创建自己的java类库并加以调用方法
- quartz集群 定时任务 改成可配置
- hadoop namenode
- Android studio 如何快速收起代码?