一、背景
之前我们学习了并发工具类CountDownLatch、Semaphone等,还有可重入锁ReentrantLock,读写锁ReetrantReadWriteLock等
它们都提供了锁的功能,只不过在实现最基本的锁功能后,又提供了其他不同的功能
而它们最基本的锁功能:都是使用AbstractQueuedSynchronizer(简称AQS)来实现
换句话说,AQS规定了锁(无论独占模式还是共享模式)需要实现哪些方法,并提供了一些通用方法(如竞争失败的线程如何进入等待队列,如何唤醒等待队列中的线程等)的具体实现,不要开发者操心。只需要开发者自己定义好共享资源的获取与释放等。
二、模板方法模式
在学习AQS之前,我们先学习一下模板方法模式
模板方法模式:一个抽象类公开定义了一系列方法,它的子类可以按照需要重写对应方法的实现,调用将以抽象类中定义的方式进行
定义比较抽象,直接看一个例子就明白了
假设从A地去B地有三种方式,坐汽车,坐火车,坐高铁
无论哪种方式都需要进行买票,乘坐,到达三个步骤
这时我们就可以使用模板方法模式了
这里注意区分模板方法,流程方法
父类FromAToB
public abstract class FromAToB {
//买票(流程方法)
public abstract void buyTicket();
//乘坐(流程方法)
public abstract void ride();
//到达(流程方法)
public abstract void arrive();
//其他通用的公共方法,由父类直接实现,子类无需重写(流程方法)
public void other() {
System.out.println("看风景");
}
//我们自己定义的模板方法
public void setOut() {
buyTicket();//买票
ride();//乘坐
other();//看风景
arrive();//到达
}
}
子类GoBuyTrain,继承父类FromAToB,重写对应的流程方法
public class GoBuyTrain extends FromAToB{
//子类重写父类的流程方法
@Override
public void buyTicket() {
System.out.println("