当前位置: 首页 > news >正文

佛山+网站建设昆明seo关键字推广

佛山+网站建设,昆明seo关键字推广,怎么把图片做超链接到网站,久久建设集团有限公司文章目录前言Semaphore原理Semaphore源码解析内部继承AQS保证同步acquire获取许可release释放许可实战演示总结前言 在多线程编码过程中,我们会用到多线程来提升运行效率。比如我们的Executors创建线程池,程序尽可能的压榨CPU资源来提升我们程序吞吐量。…

文章目录

    • 前言
    • Semaphore原理
    • Semaphore源码解析
      • 内部继承AQS保证同步
      • acquire获取许可
      • release释放许可
    • 实战演示
    • 总结

前言

在多线程编码过程中,我们会用到多线程来提升运行效率。比如我们的Executors创建线程池,程序尽可能的压榨CPU资源来提升我们程序吞吐量。但是过度的使用线程,也会将我们CPU资源榨干,从而让我们系统不能正常的提供服务。故今天我们引入JUC并发包下面的semaphore并发类,该类可以同时允许定量线程执行从而达到控制并发的目的。

Semaphore原理

Semaphore并发类提供了两个核心方法:acquire()方法和release()方法。acquire()方法表示获取一个许可,如果没有则等待,release()方法则是释放对应的许可。Semaphore维护了当前访问的个数,通过提供同步机制来控制同时访问的个数。

Semaphore源码解析

内部继承AQS保证同步

Semaphore 与AQS关系图:
在这里插入图片描述

进入java.util.concurrent 包下 Semaphore 并发类查看源码:

//继承AQS同步阻塞队列来实现同步功能
abstract static class Sync extends AbstractQueuedSynchronizer {private static final long serialVersionUID = 1192457210091910933L;Sync(int permits) {setState(permits);}final int getPermits() {return getState();}final int nonfairTryAcquireShared(int acquires) {for (;;) {int available = getState();int remaining = available - acquires;if (remaining < 0 ||compareAndSetState(available, remaining))return remaining;}}

如上所示,首先Semaphore并发内部类继承AbstractQueuedSynchronizer 同步阻塞类,所以可以得出Semaphore是通过AQS机制来保证同步。AQS不明白的同学可以看我之前的博文,大概就是内部一个state状态,获取到资源 state 就加一,释放资源 state 就减一,当 state == 0 的时候表示阻塞队列中的其他线程可以获取该资源。

继续查看源码:

/*** Creates a {@code Semaphore} with the given number of* permits and nonfair fairness setting.** @param permits the initial number of permits available.*        This value may be negative, in which case releases*        must occur before any acquires will be granted.*/
public Semaphore(int permits) {sync = new NonfairSync(permits);
}/*** Creates a {@code Semaphore} with the given number of* permits and the given fairness setting.** @param permits the initial number of permits available.*        This value may be negative, in which case releases*        must occur before any acquires will be granted.* @param fair {@code true} if this semaphore will guarantee*        first-in first-out granting of permits under contention,*        else {@code false}*/
public Semaphore(int permits, boolean fair) {sync = fair ? new FairSync(permits) : new NonfairSync(permits);
}

如源码所示,Semaphore构造方法默认提供非公平锁同步构造方法,也提供了一个用户自定义是否公平锁的构造方法。是否公平锁同步直接影响阻塞队列中的哪个线程可以获取资源,公平锁是按照阻塞顺序获取资源,非公平锁是多个线程争抢资源。当然构造方法必须传入并发许可的总数,这个总数直接影响后续我们可以同时获取多少个许可。

acquire获取许可

查看Semaphore 获取许可的源码:

//是否可以获取许可
public boolean tryAcquire() {return sync.nonfairTryAcquireShared(1) >= 0;
}
//是否可以获取许可,并提供超时获取机制
public boolean tryAcquire(long timeout, TimeUnit unit)throws InterruptedException {return sync.tryAcquireSharedNanos(1, unit.toNanos(timeout));
}
//是否可以获取多个许可,并提供超时获取机制
public boolean tryAcquire(int permits, long timeout, TimeUnit unit)throws InterruptedException {if (permits < 0) throw new IllegalArgumentException();return sync.tryAcquireSharedNanos(permits, unit.toNanos(timeout));
}
//提供一个无参获取许可方法,默认获取一个许可
public void acquire() throws InterruptedException {sync.acquireSharedInterruptibly(1);
}//不间断的获取许可,如果获取不到就阻塞
public void acquireUninterruptibly() {sync.acquireShared(1);
}
//不间断的获取多个许可,如果获取不到就阻塞
public void acquireUninterruptibly(int permits) {if (permits < 0) throw new IllegalArgumentException();sync.acquireShared(permits);
}

如源码所示,我获取许可有很多的方法。有是否可以获取许可,超时是否可以获取许可。当然还有获取许可的方法,以及阻塞获取许可的多个方法,这些方法本质上都是调用父AQS中的获取资源许可的方法,同学们可以选择自己适用的方法进行调用。

release释放许可

查看Semaphore 释放许可的源码:

//默认释放一个许可
public void release() {sync.releaseShared(1);
}
//同时释放多个许可
public void release(int permits) {if (permits < 0) throw new IllegalArgumentException();sync.releaseShared(permits);
}
//调用父AQS的释放资源的方法
public final boolean releaseShared(int arg) {if (tryReleaseShared(arg)) {doReleaseShared();return true;}return false;
}

如源码所示,Semaphore提供了多个释放许可的方法,我们可以根据实际需要选择释放许可的方法。
值得注意的是release() 方法调用了自己内部类Sync的释放资源方法,而Sync又是继承AQS阻塞队列并调用了父类doReleaseShared() 释放资源的方法。

实战演示

上面博文我们介绍了Semaphore并发类是一个同步类,它继承了AQS阻塞队列。Semaphore主要提供了acquire() 获取许可与release() 释放许可的方法,通过这两个方法我们可以实现线程并发数目的功能。下面我们简单模拟一下限制并发数目。

1、Semaphore测试类
测试类提供一个定量5的线程池,用countdownlatch 让主线程等待子线程执行完成,Semaphore保证每次只有3个线程执行。为了保证测试结果可以追溯性,我们在业务逻辑中让线程睡眠3s。

/*** Semaphore test* @author senfel* @date 2023/4/6 11:38 * @return*/
@SpringBootTest
class ConcurrentApplicationTests {/*** 日期格式*/private static DateTimeFormatter formatter = DateTimeFormatter.ofPattern("HH:mm:ss");@Testvoid testSemaphore() throws Exception {//创建线程为5的线程池ExecutorService executorService = Executors.newFixedThreadPool(5);//同时运行3个线程运行Semaphore semaphore = new Semaphore(3);//等待执行完成CountDownLatch countDownLatch = new CountDownLatch(10);for(int i = 0;i<10;i++) {executorService.execute(new Runnable() {@Overridepublic void run() {try{//获取许可semaphore.acquire();//业务逻辑executeFun();//释放许可semaphore.release();countDownLatch.countDown();}catch (Exception e){e.printStackTrace();}}});}countDownLatch.await();System.err.println("执行完成");executorService.shutdown();}/*** 执行业务方法* @author senfel* @date 2023/4/6 11:13* @return void*/private void executeFun() {try {String startTime = formatter.format(LocalDateTime.now());Thread.sleep(3000);System.err.println("当前执行线程:"+Thread.currentThread().getName()+",开始时间:"+startTime+",结束时间"+formatter.format(LocalDateTime.now()));} catch (Exception e) {e.printStackTrace();}}}

2、执行测试方法
执行testSemaphore() 方法,我们可以在控制台看到如下结果:

当前执行线程:pool-1-thread-1,开始时间:11:37:00,结束时间11:37:03
当前执行线程:pool-1-thread-3,开始时间:11:37:00,结束时间11:37:03
当前执行线程:pool-1-thread-2,开始时间:11:37:00,结束时间11:37:03
当前执行线程:pool-1-thread-2,开始时间:11:37:03,结束时间11:37:06
当前执行线程:pool-1-thread-1,开始时间:11:37:03,结束时间11:37:06
当前执行线程:pool-1-thread-3,开始时间:11:37:03,结束时间11:37:06
当前执行线程:pool-1-thread-1,开始时间:11:37:06,结束时间11:37:09
当前执行线程:pool-1-thread-4,开始时间:11:37:06,结束时间11:37:09
当前执行线程:pool-1-thread-2,开始时间:11:37:06,结束时间11:37:09
当前执行线程:pool-1-thread-5,开始时间:11:37:09,结束时间11:37:12
执行完成

根据执行结果我们可以发现每3s有3个线程执行并输出,得出结论Semaphore可以保证每次只能同时3个线程执行!!!!

总结

多线程控制并发数目工具类Semaphore内部继承AQS抽象阻塞队列,并继承了其同步获取、释放资源的方法。Semaphore提供了acquire()获取许可、release()释放许可方法,底层当然调用的是AQS内部方法来满足同步以保证限制并发线程运行数目。

http://www.ds6.com.cn/news/4451.html

相关文章:

  • 六安网站建设价格优化网站排名工具
  • 做网站的是干嘛的长春网络优化最好的公司
  • 南城微网站建设商品标题优化
  • 17网站一起做网店免费推广seo
  • 手机网站建设方案书推广优化seo
  • 专业做展会网站建立网站需要什么技术
  • 佛山网站建设设计爱站网络挖掘词
  • 山东网站建设方案制作友情链接交换方式有哪些
  • 潍坊网站建设建站网站制作软件免费下载
  • 网站登陆页面怎么做天津seo公司
  • 学做网站在什么地方学电商平台如何推广运营
  • 响应式网站一般做几个尺寸东莞市网络seo推广价格
  • 如何用自己电脑做网站测试房管局备案查询网站
  • 求一个做交通分析的底图网站网站功能优化
  • 佛山 网址开发 网站制作跨境电商怎么开店铺
  • 公司的网站费怎样做会计分录营销推广技巧
  • 南京手机网站制作如何制作一个简单的网页
  • 微信二维码制作网站seo排名赚app是真的吗
  • 建网赚网站成都网站快速排名优化
  • b2c网站建设 广州谷歌seo工具
  • 网站模板绑定域名湖北网络推广
  • 阳朔到桂林汽车时刻表seo网络培训学校
  • 建站系统搭建音乐网站广州网络推广公司
  • 新手如何做网站推广重庆人力资源和社会保障网
  • 北京网站备案拍照地址鼓楼外贸营销型网站制作公司
  • 闵行手机网站建设除了百度指数还有哪些指数
  • .net web网站开发经典软文案例100例
  • 云南旅游网站设计bt兔子磁力天堂
  • wordpress首页添加一个超链接框seo运营是做什么的
  • 开发网站建设方案2022年seo还值得做吗