java多线程与线程池-04线程池与AQS

第7章 线程池与AQS

java.util.concurrent包中的绝大多数同步工具,如锁(locks)和屏障(barriers)等,都基于AbstractQueuedSynchronizer(简称AQS)构建而成。这个框架提供了一套同步管理的通用机制,如同步状态的原子性管理、线程阻塞与解除阻塞,还有线程排队等。

在JDK1.5引入了java.util.concurrent包,其中包含多个支持中等级别线程并发的类,如可重入锁(ReentrantLock)、读锁(ReentrantReadWriteLock.ReadLock)、写锁(Reentrant-ReadWriteLock.WriteLock)、信号量(Semaphore)、屏障(CyclicBarrier)、Future对象、事件指示器以及传送队列等。这些同步类主要有如下功能:

(1)对象内部同步状态的维护(如表示锁的状态是已获取还是已释放)。

(2)更新和检查状态的操作。而且至少有一个方法会导致调用线程在同步状态被获取时被阻塞,以及在其他线程改变这个同步状态时解除线程的阻塞。

几乎任何一个知名的同步器都可以用来实现其他形式的同步器。例如,可以用可重入锁(ReentrantLock)来实现信号量(Semaphore);反之,用信号量也可以实现可重入锁。但是,这样做会带来复杂性高、开销过大、不灵活等问题,使其最终只能成为一个二流项目。而使用AQS用户可以用简洁的方式定义自己的线程同步器。

7.1 acquire与release

所有的线程同步器至少应该包含两个方法:一个是acquire,另一个是release。acquire方法阻塞调用的线程,直到同步状态允许其继续执行。而release操作则是通过某种方式改变同步状态,使得一个或多个被阻塞的线程解锁。

image-20230310171355423

在JUC包中并没有对同步器定义统一的API。因此,有些类通过Lock接口来定义(如ReentrantLock、ReentrantReadWriteLock.ReadLock、ReentrantReadWriteLock.WriteLock),而另外一些则定义了其专有的版本(如Semaphore、CountDownLatch)。因此acquire和release方法的操作,会有各种不同的形式、不同的类。例如,Lock.lock、Semaphore.acquire、CountDownLatch.await和FutureTask.get等,都会映射到acquire操作。

JUC为了支持同步器的常用功能,对所有同步类做了一致性约定,即每个同步器都应支持下面的操作:

  • 阻塞和非阻塞同步尝试(如tryLock)。
  • 可选的超时设置,让调用者可以放弃等待。
  • 通过中断取消任务,通常会分为两个版本:一个可以取消,而另一个不可以。

同步器的实现根据其状态是否独占而有所不同。独占状态的同步器,在同一时间只有一个线程可以通过阻塞点,而共享状态的同步器可以同时有多个线程进入阻塞点。通过AQS实现的同步器,必须同时支持独占与共享两种模式。

在JUC包里还定义了Condition接口,支持监视器风格的await/signal操作。Condition的操作必须与独占模式的Lock类相关。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值