一、基本概念
线程同步器是协调多个线程对共享资源的访问,AQS提供了一个基于先入先出队列实现的线程同步器基础框架,具体的线程同步器实现类只需要关注共享资源的访问控制(或者说是可共享资源数量的定义)。具体的访问模式可分为互斥访问和共享访问。
互斥访问:即共享资源仅允许一个线程进行访问。
共享访问:需要设置访问共享资源的线程数。
若所有的可用资源的均被其他线程占用,则进来的线程会放在一个等待队列中,等待其他线程释放资源,唤醒队列头部的第一个节点线程。
具体的方法实现层面,对于AQS的实现类,如ReentrantLock、CountDownLatch等,只需要自定义tryAcquire方法的实现来判断是否可以访问共享资源,以及自定义tryRelease方法的实现来释放共享资源,允许其他线程访问共享资源即可。
在多线程对资源的竞争方面,AQS默认实现是采取一种公平策略,即内部使用的是先入先出队列,线程会先进入队列中,等待有可用资源时按照进入队列的先后顺序依次被唤醒。公平策略的有限是线程不会被饿死,缺点是执行慢的线程会影响执行快的线程。
二、核心设计
主要有4大核心设计:
1.队列,将线程放在队列中,等待执行。互斥访问中,只有一个线程可以访问共享资源,其他线程需在队列中等待。
2.状态,每个线程都有一个同步状态。在互斥访问中,state通常为1,表示在任何时候,只能有一个线程对共享资源访问。例如可重入锁ReentrantLock
3.线程状态的控制,由线程的生命周期可知,当线程需要等待访问共享资源时,线程的状态从RUNABLE变成WAITING或者TIME_WAITING,退出对CPU资源的竞争。被唤醒时,则从WAITING或TIME_WAITING状态改为RUNABLE,等待CPU的调度执行,在AQS的实现中,主要是使用LockSupport这个工具类的用于阻塞和唤醒线程的相关方法来对线程的状态进行控制。
4.自旋和CAS机制实现无锁化的线程安全操作,在先入先出队列中,增删线程节点,或者更新线程节点的状态waitStatus时,主要是通过UNSAFE类提供的硬件级别的原子操作来检测条件是否满足,从而决定是执行还是等待。
无锁化的实现,避免了线程间的冲突,有效利用缓存行,提高并发性能。避免了死锁问题,因为他不再需要使用锁来协调线程的行为。