今天在看Lock,都知道相比於synchronized,多了公平鎖,可中斷等優秀性能。
但是說到可中斷這個特點,看到很多博客是這么描述的:
“與synchronized關鍵字不同,獲取到鎖的線程能夠響應中斷,當獲取到鎖的線程被中斷時,中斷異常將會被拋出,同時鎖會被釋放”
我的理解是,應該是未獲得到鎖的線程被中斷時,中斷異常將會被拋出。
看了下lockInterruptibly()的源碼
第一層
public void lockInterruptibly() throws InterruptedException {
sync.acquireInterruptibly(1);
}
第二層
public final void acquireInterruptibly(int arg)
throws InterruptedException {
if (Thread.interrupted())
throw new InterruptedException();
if (!tryAcquire(arg))
doAcquireInterruptibly(arg);
}
第3層
private void doAcquireInterruptibly(int arg)
throws InterruptedException {
final Node node = addWaiter(Node.EXCLUSIVE);
boolean failed = true;
try {
for (;;) {
final Node p = node.predecessor();
if (p == head && tryAcquire(arg)) {
setHead(node);
p.next = null; // help GC
failed = false;
return;
}
if (shouldParkAfterFailedAcquire(p, node) &&
parkAndCheckInterrupt())
throw new InterruptedException();
}
} finally {
if (failed)
cancelAcquire(node);
}
}
其實就是調用lockInterruptibly()時,第二層中判斷當前線程是否中斷Thread.interrupted() 如果是,拋異常
以及第三層中 一個for(;;)循環一直判斷當前線程是否有中斷標志。(代碼中大字標識部分)
所以不是很理解很多博客中說的這種情況。
總結:lock中的可中斷特性是基於lockInterruptibly()方法的,它是對於那些未競爭的到鎖,而 可以被外部調用interrupt()來中斷,從而達到不在等候鎖資源,不再去競爭鎖