同步器AQS解析
什么是同步器?
多线程并发执行,通过某种共享状态来同步,当共享状态满足某种条件,才能触发线程开始执行操作。
AbstractQueuedSynchronizer(AQS)
这是一个抽象类,它提供多线程下不同共享模式的操作,实现它可以自定义同步器。
可以看出,ReentrantLock和ReentrantReadWriteLock的内部类都是继承于这个抽象类。
public abstract class AbstractQueuedSynchronizer extends AbstractOwnableSynchronizer implements java.io.Serializable { private static final long serialVersionUID = 7270805090050340580L; // 底层操作 private static final Unsafe unsafe = Unsafe.getUnsafe(); // 线程节点 static final class Node { static final Node SHARED = new Node(); static final Node EXCLUSIVE = null; static final int CANCELLED = 1; static final int SIGNAL = -1; static final int CONDITION = -2; static final int PROPAGATE = -3; volatile int waitStatus; volatile Node prev; volatile Node next; volatile Thread thread; Node nextWaiter; final boolean isShared() { return nextWaiter == SHARED; } final Node predecessor() throws NullPointerException { Node p = prev; if (p == null) throw new NullPointerException(); else return p; } Node() { } Node(Thread thread, Node mode) { this.nextWaiter = mode; this.thread = thread; } Node(Thread thread, int waitStatus) { this.waitStatus = waitStatus; this.thread = thread; } } // 头结点 private transient volatile Node head; // 尾节点 private transient volatile Node tail; // 共享状态 private volatile int state; // 独占锁获取 protected boolean tryAcquire(int arg) { throw new UnsupportedOperationException(); } // 独占锁释放 protected boolean tryRelease(int arg) { throw new UnsupportedOperationException(); } // 共享锁获取 protected int tryAcquireShared(int arg) { throw new UnsupportedOperationException(); } // 共享锁释放 protected boolean tryReleaseShared(int arg) { throw new UnsupportedOperationException(); } // 快速判断被线程独占 protected boolean isHeldExclusively() { throw new UnsupportedOperationException(); } // 获取同步状态 protected final int getState() { return state; } // 设置同步状态 protected final void setState(int newState) { state = newState; } // 原子操作同步状态 protected final boolean compareAndSetState(int expect, int update) { return unsafe.compareAndSwapInt(this, stateOffset, expect, update); } // 其他方法... }
以上就是AQS里关键的几个需要重写的方法,这里没有将方法定义为abstract,而是方法只抛出一个异常,这是因为AQS有很多方法可以重写,而又不是每个都需要,所以就没有写成abstract。