上两天一直在更新ReentrantLock得源码阅读。今天就更新一下在java.util.concurrent中最重要得基础类AbstractQueuedSynchronizer简称AQS类。
通过读源码得注释可以了解到,这个类是为实现依赖于先进先出(FIFO)等待队列实现阻塞锁以及同步器(信号灯,事件等)提供了一个框架。换而言之,这个类单独拿出来并没有什么实际意义,只是提供了一个框架,。这个类的设计目标就是依靠一个原子int state值来表示状态。从而建立了一个对大多数同步器都有用的基础。
子类必须定义更改此状态的受保护的方法,并且定义次该状态对于此对象的获取或者释放意味着什么。鉴于这些,此类中的其他方法就可以执行排队和阻塞机制。子类可以维护其他状态字段,但是为了获得同步儿只追踪使用getState()、setState(int)、和compareAndSetState(int, int)这几个方法来以原子更新的方式操作int state的值。
子类应该被定义为非公共的内部帮助类,用于实现其封闭类的同步属性。类AbstractQueuedSynchronizer并不实现任何同步接口。它定义了acuqireInterruptibly等方法,这些方法可以被具体的锁和相关的公布前适当的调用来实现他们的公共方法。
此类支持默认的独占 模式和共享 模式之一,或者二者都支持。处于独占模式下时,其他线程试图获取该锁将无法取得成功。在共享模式下,多个线程获取某个锁可能(但不是一定)会获得成功。此类并不“了解”这些不同,除了机械地意识到当在共享模式下成功获取某一锁时,下一个等待线程(如果存在)也必须确定自己是否可以成功获取该锁。处于不同模式下的等待线程可以共享相同的 FIFO 队列。通常,实现子类只支持其中一种模式,但两种模式都可以在(例如)ReadWriteLock 中发挥作用。只支持独占模式或者只支持共享模式的子类不必定义支持未使用模式的方法。
此类通过支持独占模式的子类定义了一个嵌套的 AbstractQueuedSynchronizer.ConditionObject 类,可以将这个类用作 Condition 实现。isHeldExclusively() 方法将报告同步对于当前线程是否是独占的;使用当前 getState() 值调用 release(int) 方法则可以完全释放此对象;如果给定保存的状态值,那么 acquire(int) 方法可以将此对象最终恢复为它以前获取的状态。没有别的 AbstractQueuedSynchronizer 方法创建这样的条件,因此,如果无法满足此约束,则不要使用它。AbstractQueuedSynchronizer.ConditionObject 的行为当然取决于其同步器实现的语义。
此类为内部队列提供了检查、检测和监视方法,还为 condition 对象提供了类似方法。可以根据需要使用用于其同步机制的 AbstractQueuedSynchronizer 将这些方法导出到类中。
此类的序列化只存储维护状态的基础原子整数,因此已序列化的对象拥有空的线程队列。需要可序列化的典型子类将定义一个 readObject 方法,该方法在反序列化时将此对象恢复到某个已知初始状态。
PS:借鉴小D课堂java并发课程的笔记以及自己翻译源码注释写的,欢迎同学提出问题并指正