我们常说的“并发包”指的是java.util.concurrent这个包,后面简称 J.U.C,里面包含大量多线程和并发编程的工具。J.U.C 包是 JDK 1.5 版本引入,本文所有内容基于 JDK11。

工具类

工具包内主要有这几个工具:计数器CountDownLatch、回环栅栏(光看名字估计一头雾水)CyclicBarrier、信号量Semaphore、创建线程池的Executors,最后一个交换数据的Exchanger。本章几个工具的原理都是基于 AQS,关于 AQS 和ReentrantLock,都有单独的文章解读,就不专门介绍了。

CountDownLatch

一个计数器,常见这样一种场景:多个任务分发个不同的线程去执行,全部执行完毕后回到主线程。当然有不同的实现方式,用CountDownLatch实现起来就很简单:

int taskNum = 20;CountDownLatch countLatch = new CountDownLatch(taskNum);for (int i = 0; i < taskNum; i++) {new Thread(() -> {try {Thread.sleep(200); //假装做了点什么System.out.println(Thread.currentThread().getName() + "执行完毕");} catch (InterruptedException e) {e.printStackTrace();}countLatch.countDown();  // 减1操作}).start();}try {countLatch.await(); // 阻塞线程,直至countDown方法调用次数等于taskNum,才会释放线程。for循环次数必须大于等于taskNumSystem.out.println("全部任务执行完毕");} catch (InterruptedException e) {e.printStackTrace();}

Seamphore

信号量,类似于控制并发的时候用到的“令牌桶”算法,通过控制信号总数,不断释放和回收信号来控制并发数量。假设有这么一个场景,假设我们有五个通道可以执行任务,任务总数是 40,所以同一时刻只能有最多五个线程执行,其余的要等待,因此我们使用Seamphore来不断方法许可和收回许可:

Semaphore semaphore = new Semaphore(5);for (int i = 0; i < 40; i++) {new Thread(() -> {try {semaphore.acquire();  // 获取许可,获取失败则进入阻塞System.out.println(Thread.currentThread().getName() + "取得许可,开始执行任务");Thread.sleep(new Random().nextInt(2000));System.out.println(Thread.currentThread().getName() + "任务完成,释放许可");semaphore.release();  // 释放许可。释放后激活阻塞线程去争取许可} catch (InterruptedException e) {e.printStackTrace();}}).start();}

CyclicBarrier

回环栅栏光看名字不好理解,其实作用很上面的计数器类似,有点类似于 Java 虚拟机中的“安全点”。执行一个任务的时候,所有线程到达栅栏之后停止,等待所有其他线程都到达这个点,然后一起进入下一阶段。与计数器不同的是,CyclicBarrier可以重复使用,举个栗子:
用于协调多个线程同步执行操作的场合,所有线程等待完成,然后一起做事情( 相互之间都准备好,然后一起做事情 )
例如百米赛跑,必须等待所有运动员都准备好了,才能比赛。

CyclicBarrier cyclicBarrier = new CyclicBarrier(20);for (int i = 0; i < 20; i++) {new Thread(() -> {long timeStamp = System.currentTimeMillis();try {Thread.sleep(new Random().nextInt(2000));System.out.println(Thread.currentThread().getName() + ":一阶段任务完成,花费了" + (System.currentTimeMillis() - timeStamp) + "毫秒,开始等待其他线程");cyclicBarrier.await();System.out.println(Thread.currentThread().getName() + ":所有线程执行完成,开始下一阶段");timeStamp = System.currentTimeMillis();Thread.sleep(new Random().nextInt(2000));System.out.println(Thread.currentThread().getName() + ":二阶段任务完成,花费了" + (System.currentTimeMillis() - timeStamp) + "毫秒,开始等待其他线程");cyclicBarrier.await();System.out.println(Thread.currentThread().getName() + ":所有线程任务完成");} catch (InterruptedException | BrokenBarrierException e) {e.printStackTrace();}}).start();}

Exchanger

交换器顾名思义,就是用来交换数据,理解和使用起来是最简单的,但是内部实现很精巧复杂。使用很简单,只有两个方法,作用就是两个线程在一个安全点交换数据,产生数据慢的那个会阻塞等待。

Exchanger<Integer> exchanger = new Exchanger<>();new Thread(() -> {int num = new Random().nextInt(1000);System.out.println("交换之前:Thread1:" + num);try {num = exchanger.exchange(num);System.out.println("交换完毕:Thread1:" + num);} catch (InterruptedException e) {e.printStackTrace();}}).start();new Thread(() -> {int num = new Random().nextInt(1000);System.out.println("交换之前:Thread2:" + num);try {Thread.sleep(2000);num = exchanger.exchange(num);System.out.println("交换完毕:Thread2:" + num);} catch (InterruptedException e) {e.printStackTrace();}}).start();

Java并发包学习(CountDownLatch,Seamphore,CyclicBarrier,Exchanger)相关推荐

  1. Java并发编程:CountDownLatch、CyclicBarrier和Semaphore

    2019独角兽企业重金招聘Python工程师标准>>> Java并发编程:CountDownLatch.CyclicBarrier和Semaphore 在java 1.5中,提供了一 ...

  2. [Java并发包学习八]深度剖析ConcurrentHashMap

    转载----http://qifuguang.me/2015/09/10/[Java并发包学习八]深度剖析ConcurrentHashMap/ HashMap是非线程安全的,并发情况下使用,可能会导致 ...

  3. [Java并发包学习]深度剖析ConcurrentHashMap

    [Java并发包学习]深度剖析ConcurrentHashMap 概述 还记得大学快毕业的时候要准备找工作了,然后就看各种面试相关的书籍,还记得很多面试书中都说到: HashMap是非线程安全的,Ha ...

  4. Java并发编程:CountDownLatch、CyclicBarrier和 Semaphore

    2019独角兽企业重金招聘Python工程师标准>>> 在java 1.5中,提供了一些非常有用的辅助类来帮助我们进行并发编程,比如CountDownLatch,CyclicBarr ...

  5. Java 线程同步组件 CountDownLatch 与 CyclicBarrier 原理分析

    1.简介 在分析完AbstractQueuedSynchronizer(以下简称 AQS)和ReentrantLock的原理后,本文将分析 java.util.concurrent 包下的两个线程同步 ...

  6. Java并发编程之CountDownLatch、CyclicBarrier和Semaphore

    前言 本文为对CountDownLatch.CyclicBarrier.Semaphore的整理使用 CountDownLatch CountDownLatch类位于java.util.concurr ...

  7. java 并发包学习_Java学习笔记—多线程(java.util.concurrent并发包概括,转载)

    一.描述线程的类:Runable和Thread都属于java.lang包 二.内置锁synchronized属于jvm关键字,内置条件队列操作接口Object.wait()/notify()/noti ...

  8. 工具资源 Java并发编程:CountDownLatch、CyclicBarrier和 Semaphore

    内容转载自:http://www.importnew.com/21889.html#comment-636799 转载于:https://www.cnblogs.com/qinshou/p/81196 ...

  9. 2021年8月12日-------Java从基础到项目教程,Java全栈学习路线,帮你省去培训机构的2万块钱。

    余生很贵,请努力活成自己想要的样子. 如何进行学习,别着急,我整理全栈的Java学习路线.帮你吊打面试官. 转载自一位大佬 首先是Java的知识点 一阶段:JavaSE基础 第一步:夯实Java基础语 ...

最新文章

  1. A Neural Probabilistic Language Model 论文阅读及实战
  2. iOS性能分析-Xcode Instruments Allocations 分析APP内存使用情况
  3. 【机器学习】Apriori 算法进行关联分析和FP-growth算法
  4. 2018-2019-1 20165236《信息安全系统设计基础》第八周学习总结
  5. 网友反映摩拜单车无法扫码 回应:系技术问题 现已恢复服务
  6. centos ssh配置使用
  7. 如何 给给软件开发 添加 代理_如何从“菜鸟码农”变成“一线架构师”?
  8. 转 常用C#正则表达式收集。
  9. vs.net已经检测到制定的WEB服务器运行的不是ASP.NET1.1版,你无法运行ASP.NET WEB应用程序或服务...
  10. 会计计算机学什么软件有哪些,会计一般学什么软件有哪些
  11. 冰点还原精灵如何安装
  12. 通过CSS美化Web页面
  13. VMware Workstation虚拟机环境下Xubuntu系统如何设置中文
  14. 周集中团队Nature子刊中网络图布局的R语言可视化复现
  15. 【成功】qlv转MP4,超简单方法
  16. win、linux、unix查看系统主机名
  17. 刷脸支付广泛应用于无人领域
  18. 从微博个性图标里学Android动态更换
  19. 计算机论文写作提纲怎么写,计算机算法论文提纲 计算机算法论文大纲如何写...
  20. if语句的三种格式(使你更加清晰)

热门文章

  1. PHP使用openoffice实现word,ppt,Excel在线转PDF浏览。windows和linux系统不同的解决方案
  2. ku115上实现adc12dj3200 配置,jesd204b接口,单通道采集模式
  3. 软件工程(软件计划)
  4. 视频融合平台EasyCVR首路录像无法播放是什么原因?该如何解决?
  5. max9286 四合一_MAX9286+HI3519 +MAX96705方案分享
  6. Android学习笔记:Android基础知识点(不断更新中)
  7. SAM9X60 curiosity开发板,SYSFS文件系统控制板载三色Led
  8. Codeforces 1546 D. AquaMoon and Chess —— 组合数学,一点点想法
  9. 医疗行业售前100问之第2问:医院有几张网?
  10. 【市场分析1】FinTech之香港虚拟银行VB