java aqs总结

本文详细介绍了Java并发基础组件AQS(AbstractQueuedSynchronizer),包括其基本结构、核心思想及在ReentrantLock中的应用。AQS使用模板方法模式,维护了一个双端队列,用于线程同步。ReentrantLock分为公平锁和非公平锁,其加锁、解锁流程各有特点。文章通过实例解析了节点状态、等待队列管理等关键概念,揭示了AQS如何实现线程的阻塞和唤醒。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

前言

这篇文章描述的是关于java Aqs框架的整体个人总结,从数据结构,lock接口的角度出发

一、什么是AQS

AbstractQueuedSynchronizer
是大部分java并发工具的基本框架,提供了acquire(获取锁),release(释放锁)的方法。
它的核心思想:
如果请求的资源是空闲的,那就将当前请求的线程设置为有效的工作线程,并将共享资源设置为锁定状态,如果共享资源被暂用,就需要一定的阻塞等待机制来保证锁的分配。

二、AQS的基本结构

1.内部子类node

Node prev(用于保存前继节点),
Node tail(用于保存后续节点),还有两个Node分别标记当前是共享锁还是独占锁。
Thread thread(保存当前节点关联的线程地址)。
int waitStatus(用来表示当前节点的状态)。

1.1 节点状态的值

1:线程已取消调度
0:初始话状态,未锁定
-1:后继结点在等待当前结点唤醒。后继结点入队时,会将前继结点的状态更新为SIGNAL
-2:结点等待在Condition上,当其他线程调用了Condition的signal()方法后,CONDITION状态的结点将从等待队列转移到同步队列中,
等待获取同步锁
-3:共享模式下,前继结点不仅会唤醒其后继结点,同时也可能会唤醒后继的后继结点。

2 父类的主要属性

int state(用来控制整体可重入的情况)。
Node head;
Node tail;
还有各种int类型的偏移量:
在这里插入图片描述

3 小结

从数据结构看出来,它内部是一个双向链表,初始化的时候会在先初始化一个头节点和一个尾节点,两节点的指针互相引用。
很多资料都说它最终维护的是一个队列,那从哪些地方能看出来他维护的是一个队列呢。

三、从ReentrantLock学习AQS

1. ReentrantLock中的内部类含义

1.Sync 继承AbstractQueuedSynchronizer,内部默认实现的是非公平锁的加锁方法。
2.NonfairSync继承Sync,代表非公平锁,加锁方式调用的是Sync的加锁方法。
3.FairSync继承Sync,代表公平锁,加锁方式是自己实现的公平锁的加锁方式

2. ReentrantLock非公平锁的加锁流程

内部执行Sync的lock方法,本质上是调用aqs的acquire方法,在调用子类的tryAcquire方法通过state判断该重入锁的状态,通过cas修改state值,修改成功后,当前线程成功获取到锁,将当前线程设置为独占线程。修改失败,获取一个新的state值,若state值小于0,获取锁失败,新建节点并放入队列中。

流程图大致如下:
在这里插入图片描述

3. ReentrantLock公平锁加锁流程

大致流程与非公平锁一样,但是会判断尝试获取锁的节点是否是当前队列的有效结点(一般来说是头结点的后面一个),如果是,才会获得锁

4. ReentrantLock解锁流程

从源码角度可以看出:
内部执行Sync的release方法,该方法是继承AQS,而在release中会调用子类实现的tryRelase方法,释放锁过程中并不会区分公平锁和非公平锁。 释放成功后,找到队列中下一个节点状态<=0的节点,并将其unpark。

流程图如下:
在这里插入图片描述

5. 获取锁失败,是如何加入等待队列的呢?

通过当前线程和锁模式创建一个节点,将node的prev指向tail,在通过cas将队列中尾结点的指针指向node。

6. 小结

从上述流程可以知道,因为每次插入节点,都是从尾结点的前一个index插入因为尾结点是虚节点,释放锁也是将有效节点变为虚节点(head节点),所以他维护的是一个先进先出的队列。

四、总结

java中用到aqs的并发工具类还有很多比如CountDownLatch和CyclicBarrier;他们的加锁和释放锁的流程 都是围绕着节点的waitStatus进行的,而对应调用的方法都是AQS的tryAcquire和tryRelease,当然AQS也支持共享锁,其对应的api也是tryAcquireShared和tryReleaseShared。
当然,这篇文章并不是所有AQS的知识点,只是博主认为较为重要的罢了。

五、提问

AQS用的是哪种设计模式?
答:模板方法模式

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值