首先看看关于Semaphore的UML图:

    

  从上图看,信号量的实现原理与锁类似,是基于AQS的;有公平与非公平之分。当初始的资源数为1时就退化为排它锁了,资源总数即state的初始值,在acquire里对state变量进行CAS减操作,减到0之后,线程阻塞;在release里对state变量进行CAS加操作。
  下面简单示范Semaphore的使用:
  1)

    

  2)

    

  3)

      

  通过Semaphore的UML图可知,其使用AQS构建其阻塞类,在Java并发基础之AbstractQueuedSynchronizer(AQS) - 池塘里洗澡的鸭子 - 博客园 (cnblogs.com)中大致介绍了AQS的模板方法,那么Semaphore是如何利用AQS构建阻塞类的呢?

  1、创建信号量对象:

    构造方法有两个,,本文中案例使用第一个构造函数:

    

    最终使用AQS中setState将参数传递给AQS中的state:Semaphore使用AQS类型的同步状态持有当期可用许可的数量。

      

  2、获取acquire

    

    Semaphore类中重写tryAcquireShared方法首先计算剩余许可的数量,如果没有足够的许可,会返回一个值表示获取操作失败。如果还有充足的许可剩余,tryAcquireShared会使用compareAndSetState尝试原子地递减许可的计数。如果成功(这意味着自从许可计数到最后一次看到后都没有被改变过),会返回一个值表示获取操作成功。返回值同样加入了是否运行其他共享获取尝试能否成功的信息,如果可以的话,其他等待的线程同样会解除阻塞。

    注意tryAcquireShared方法内部使用无限循环,即无论是否有足够的许可数量,在相应获取操作时,该循环都会终止。尽管任何给定的compareAndSetState调用都可能由于与另一个线程的竞争而失败,但是这种场景它会重试。在重试过合理的次数后,两个终止条件中的一个会变成真。

  3、释放release

    类似地,跟踪到tryReleaseShared会递增许可计数,潜在地解除等待中的线程的阻塞并不断地重试直到成功地更新。tryReleaseShared的返回值表明释放操作释放可以解除其他线程的阻塞。

    

  

JUC并发工具类之Semaphore控制并发线程数的更多相关文章

  1. Java并发(十五):并发工具类——信号量Semaphore

    先做总结: 1.Semaphore是什么? Semaphore(信号量)是用来控制同时访问特定资源的线程数量,它通过协调各个线程,以保证合理的使用公共资源. 把它比作是控制流量的红绿灯,比如XX马路要 ...

  2. 【Java并发工具类】Semaphore

    前言 1965年,荷兰计算机科学家Dijkstra提出的信号量机制成为一种高效的进程同步机制.这之后的15年,信号量一直都是并发编程领域的终结者.1980年,管程被提出,成为继信号量之后的在并发编程领 ...

  3. Java多线程并发工具类-信号量Semaphore对象讲解

    Java多线程并发工具类-Semaphore对象讲解 通过前面的学习,我们已经知道了Java多线程并发场景中使用比较多的两个工具类:做加法的CycliBarrier对象以及做减法的CountDownL ...

  4. Java并发工具类(四):线程间交换数据的Exchanger

    简介 Exchanger(交换者)是一个用于线程间协作的工具类.Exchanger用于进行线程间的数据交换.它提供一个同步点,在这个同步点两个线程可以交换彼此的数据.这两个线程通过exchange方法 ...

  5. j.u.c系列(10)---之并发工具类:Semaphore

    写在前面 Semaphore是一个计数信号量,它的本质是一个"共享锁". 信号量维护了一个信号量许可集.线程可以通过调用acquire()来获取信号量的许可:当信号量中有可用的许可 ...

  6. 1.3.4 并发工具类CountDownLatch/Semaphore/CyclicBarrier/FutureTask

    CountDownLatch的2个用途: 1. 所有线程都到达相同的起跑线后,再一起开始跑(并非同时开始,而是队列中一个唤醒另一个)[此情况需到达起跑线后再调用await()等待其他线程] 2. 所有 ...

  7. Java并发—并发工具类

    在JDK的并发包里提供了几个非常有用的并发工具类.CountDownLatch.CyclicBarrier和Semaphore工具类提供了一种并发流程控制的手段,Exchanger工具类则提供了在线程 ...

  8. JUC学习笔记--JUC中并发工具类

    JUC中并发工具类 CountDownLatch CountDownLatch是我目前使用比较多的类,CountDownLatch初始化时会给定一个计数,然后每次调用countDown() 计数减1, ...

  9. JUC 常用4大并发工具类

    什么是JUC? JUC就是java.util.concurrent包,这个包俗称JUC,里面都是解决并发问题的一些东西 该包的位置位于java下面的rt.jar包下面 4大常用并发工具类: Count ...

随机推荐

  1. CentOS6.4安装Zookeeper-3.4.12图解教程

    注:图片如果损坏,点击文章链接:https://www.toutiao.com/i6595380916590215683/ 安装工具 VMware_workstation_full_12.5.2 Ce ...

  2. 关于 cannot create Parameters: [] 报错问题的解决方法

    其实在Sort类中添加无参构造就可以解决 我自己写的是Sort类,其它情况得视你们自己写的类决定 至于为什么也不是很清楚

  3. STC8H开发(四): FwLib_STC8 封装库的介绍和注意事项

    目录 STC8H开发(一): 在Keil5中配置和使用FwLib_STC8封装库(图文详解) STC8H开发(二): 在Linux VSCode中配置和使用FwLib_STC8封装库(图文详解) ST ...

  4. kafka时间轮简易实现(二)

    概述 上一篇主要介绍了kafka时间轮源码和原理,这篇主要介绍一下kafka时间轮简单实现和使用kafka时间轮.如果要实现一个时间轮,就要了解他的数据结构和运行原理,上一篇随笔介绍了不同种类的数据结 ...

  5. Blinn-Phong反射模型实践(web实现)

    Blinn-Phong反射模型实践(web实现) games101 第四次作业 最终完成带贴图的 Blinn-Phong 模型,产生光照效果 完成了 不带贴图的 Blinn-Phone 反射模型 带贴 ...

  6. MySQL提权之mof提权

    mof提权原理 关于 mof 提权的原理其实很简单,就是利用了 c:/windows/system32/wbem/mof/ 目录下的 nullevt.mof 文件,每分钟都会在一个特定的时间去执行一次 ...

  7. 应用层:http请求报文和响应报文

    1.http请求报文 请求报文由请求行.报文头.空行.报文体组成. 请求行可分为请求方法.请求URL.HTTP协议及版本. 举例1: GET / HTTP/1.1\nHost: 220.181.38. ...

  8. 【刷题-PAT】A1112 Stucked Keyboard (20 分)

    1112 Stucked Keyboard (20 分) On a broken keyboard, some of the keys are always stucked. So when you ...

  9. 【转载】ASP.NET前台代码绑定

    ASP.NET前台代码绑定后台变量方法总结http://www.cnblogs.com/lerit/archive/2010/10/22/1858007.html ASP.NET前台无法访问后台int ...

  10. Chrome本地跨域请求设置,实现HTML模板页

    按照需求,公司现在需要通过第三方的API反馈的数据,进行在本地就可以打开的静态页面程序(完全脱离IIS等服务器).为了更好的维护项目,需要实现静态HTML引入HTML模板,完成ASP.NET模板页的类 ...