一、面试题
- 第一个问题:
–背过!利用以下方法:
LockSupport互相在5的时候指定对方锁定解锁。(LockSupport用法在上篇笔记中) - 第二个问题
–背过!利用以下方法:
①Lock lock = new ReentrantLock(); 声明锁
②Condition producer = lock.newCondition() 这里的newCondition()相当于新增了一个等待队列,这个队列中的线程抢一把同步锁
③producer.await() producer这个等待队列所属的线程阻塞
④producer.singalAll() producer这个等待队列中的所有线程全部唤醒 - 第三个问题:
问:两个线程,一个输出1-26,一个输出A-Z,最终效果交替输出(例:A1B2C3…)
答:未来笔记会补充,未完待续…
二、AQS(CLH)源码分析,AQS从的继承,从上到下为父到子
- AQS内部构造图
AQS内部有一个volatile的int类型的值叫state;初始是0,如果变成了1代表这把同步锁被人抢走了,再往上涨说明重入(拿到锁的线程在锁内又拿到了这个锁)。
AQS内部还维护了一个队列,是一个双向链表,链表中有节点node,每个node中是一个Thread线程,链表中有next下一个和prev上一个。
因为是非公平锁(NonfairSync()方法调用进来的),来了新的线程发现state是0,则抢锁改为1(setState()),若没抢到则进入链表等待。
AQS底层用了Template Method 模板方法、Callback Function回调方法,这两个是同一个设计模式,模板钩子函数,代表着父类写的一个方法没有具体实现什么,实际上用子类重写实现。
往队列中加东西时使用compareAndSetState()方法。
nonfairTryAcquire()方法,如下图,所以说AQS其实是使用了CAS和volatile(本类中volatile修饰了state)
北京马士兵教育学习笔记整理