AQS系列之AbstractQueuedSynchronizer基础分析
AQS系列之以排斥锁分析
AQS系列之共享锁解析
AQS系列之共享锁的应用解析:Semaphore
AQS系列之共享锁的应用解析:CountDownLatch
AQS系列之排斥锁的应用解析:ReentrantLock
AQS系列之排斥锁和共享锁的结合:ReentrantReadWriteLock
AQS系列之Condition解析
一、简介
Condition是AQS中基于排斥锁的另一应用,其await和sign,signAll方法可以用于替代Object的wait和notify,notifyAll方法。
具体实现类是AbstractQueuedSynchronizer的内部类ConditionObject。
1. 基本结构
/** First node of condition queue. */
private transient Node firstWaiter;
/** Last node of condition queue. */
private transient Node lastWaiter;
可以看到,其数据结构主要还是一个队列,称之为条件队列。
具体的,在Node类里,我们是通过Node nextWaiter;
字段将队列关联起来的。
由于condition是基于排斥锁的,所以该字段只针对排斥节点有效,当共享节点时该字段固定位一个特殊值。我们可以根据该字段判断节点类型,这和前面几篇文章的分析里相吻合。
final boolean isShared() {
return nextWaiter == SHARED;
}
另外,前面文章对节点类的分析中已经提到,节点状态有一个特殊值static final int CONDITION = -2;
,用于表示同步队列中的节点。
二、等待await
同样的,Condition的await也有不少的方法,包括不响应中断的,带超时的等待,这里我们只介绍一个void await() throws InterruptedException;
1. public final void await() throws InterruptedException
public final void await() throws InterruptedException {
//1. 响应中断
if (Thread.interrupted())
throw new InterruptedException();
//2. 同步队列添加节点
Node node = addConditionWaiter();
//3. 释放锁
long savedState = fullyRelease(node);
int interruptMode = 0;
//4.不在同步队列中,阻塞线程
while (