Java并发工具AQS条件队列Condition实现详解,linux驱动开发入门

本文深入剖析了Java并发工具AQS的内部类ConditionObject,详细解释了Condition的await()和signal()方法的工作原理。ConditionObject作为条件队列,实现了java.util.concurrent.locks.Condition接口,其单链表结构用于存储等待线程。线程在await()时会释放锁并进入条件队列,被signal()时从条件队列转移到锁队列并唤醒。文章还对比了Lock与Condition的区别,强调Condition无自旋特性,适合于在特定条件满足时唤醒线程。对于面试者,理解这一机制将有助于提升面试表现。
摘要由CSDN通过智能技术生成

lock.lock();

try {

while ( 某条件A ) {

condition.await();

}

// 条件A满足时应执行的代码

} finally {

lock.unlock();

}

以上代码中的condition实际就是ConditionObject类。

首先,分析其声明:

public class ConditionObject implements Condition, java.io.Serializable {

1. 首先,它实现了

java.util.concurrent.locks.Condition接口,表示自己是一个条件队列。作为内部类,它没有被static关键字修饰,表示它不能脱离外部的AQS类独立存在,必须与外部类AQS实例建立关联。

2. 然后,它设置了一个单链表,firstWaiter字段指向链表的头结点,lastWaiter指向尾结点。最先开始等待的线程位于头结点,最后等待的线程位于尾结点。

Java并发工具AQS条件队列Condition实现详解

锁队列与条件队列

3. 接下来我们分析条件队列中的两个最核心的两个方法 signal 和 await()。至于signalAll,它与signalAll()几乎一致,区别只在于signal()只处理一个线程,而signalAll()处理条件队列中的所有线程。而awaitUninterruptibly(), awaitNanos(), awaitUntil()等awaitX()方法都与await()类似。

假设有以下代码:

Lock lock1 = new ReentrantLock();

Condition condtion1 = lock1.newCondition();

// 线程1调用下面这段代码:

lock1.lock();

while(某个条件) {

condition1.await();

}

lock1.unlock();

参照await的代码进行分析。首先,await()可以响应线程中断,所以一开始先判断这个时候有没有被中断(即await还没开始任何操作就遇到了中断,也许是不耐烦的用户操作引起的)。然后,把当前线程放入条件队列,释放之前已持有的锁(锁中的状态保存到线程的本地变量)。再然后,不断的查询代表当前线程的结点是否已经在锁队列上,如果不在锁队列上则阻塞。因为,把当前线程结点移到锁队列上的一定是另外一个线程(通过调用signal())。当阻塞唤醒(即从LockSupport

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值