【多线程】ReentrantLock 源码阅读

483 阅读2分钟

ReentrantLock 类实现了自 Lock 接口,先看下 Lock 接口中提供的主要方法:

  • lock() 获得锁,如果锁不可用,则当前线程进入休眠状态,直到获得锁为止。Lock 的实现类可以检测到对锁的错误使用并抛出异常。
  • unlock() 释放锁,通常情况下,只有锁的持有者可以释放它。
  • newCondition() 返回一个绑定到该 Lock 实例的新条件实例。

接下来从内部类、构造函数、类方法这三个方向,来说明介绍 ReentrantLock 类

1. 内部类

ReentrantLock 类中定义里三个内部类

1) Sync 类

Sync 继承自 AbstractQueuedSynchronizer 抽象类,主要有以下方法:

  • lock() 获得锁
  • nonfairTryAcquire(int acquires),非公平方式获取锁
  • tryRelease(int releases),尝试释放锁,如果当前线程不是独占线程,则会抛出异常
  • newCondition(),返回一个新条件实例

2) NonfairSync 类

继承自 Sync 类,采用非公平策略获取锁,重写 lock()、tryAcquire(int acquires) 两个方法。 先尝试获取资源,如果资源恰好空闲,则当前线程获取,否则加入队列尾部。

3) FairSync 类

继承自 Sync 类,采用公平策略获取锁,重写 lock()、tryAcquire(int acquires) 两个方法 先判断队列中是否有等待时间更长的线程,如果有则将该线程加入到队列的尾部,以使得等待时间最久的线程获得锁,达到公平的目的。

2. 构造函数

ReentrantLock 类的两个构造函数:

1) ReentrantLock()

生成一个 NonfairSync 实例,以非公平方式获取锁

3) ReentrantLock(boolean fair)

以 fair 参数来决定生成的哪个 Sync 实例

  • fair = true, 生成 FairSync 实例
  • fair = false, 生成 NonfairSync 实例

3. 类方法

ReentrantLock 类中的方法最终都转换为了对 Sync 对象的操作。关于对 Sync 类的操作,后续介绍 AbstractQueuedSynchronizer 抽象类的时候再做介绍。