java.util.concurrent.locks.Lock 源碼: html
package java.util.concurrent.locks; import java.util.concurrent.TimeUnit; public interface Lock { void lock(); void lockInterruptibly() throws InterruptedException; boolean tryLock(); boolean tryLock(long time, TimeUnit unit) throws InterruptedException; void unlock(); Condition newCondition(); }
全部已知實現類:java
ReentrantReadWriteLock.ReadLock, 編程
ReentrantReadWriteLock.WriteLockapi
Lock
實現提供了比使用 synchronized
方法和語句可得到的更普遍的鎖定操做。此實現容許更靈活的結構,能夠具備差異很大的屬性,能夠支持多個相關的 Condition
對象。併發
鎖是控制多個線程對共享資源進行訪問的工具。一般,鎖提供了對共享資源的獨佔訪問。一次只能有一個線程得到鎖,對共享資源的全部訪問都須要首先得到鎖。不過,某些鎖可能容許對共享資源併發訪問,如 ReadWriteLock
的讀鎖。工具
synchronized
方法或語句的使用提供了對與每一個對象相關的隱式監視器鎖的訪問,但卻強制全部鎖獲取和釋放均要出如今一個塊結構中:當獲取了多個鎖時,它們必須以相反的順序釋放,且必須在與全部鎖被獲取時相同的詞法範圍內釋放全部鎖。this
雖然 synchronized
方法和語句的範圍機制使得使用監視器鎖編程方便了不少,並且還幫助避免了不少涉及到鎖的常見編程錯誤,但有時也須要以更爲靈活的方式使用鎖。例如,某些遍歷併發訪問的數據結果的算法要求使用 "hand-over-hand" 或 "chain locking":獲取節點 A 的鎖,而後再獲取節點 B 的鎖,而後釋放 A 並獲取 C,而後釋放 B 並獲取 D,依此類推。Lock
接口的實現容許鎖在不一樣的做用範圍內獲取和釋放,並容許以任何順序獲取和釋放多個鎖,從而支持使用這種技術。spa
隨着靈活性的增長,也帶來了更多的責任。不使用塊結構鎖就失去了使用 synchronized
方法和語句時會出現的鎖自動釋放功能。在大多數狀況下,應該使用如下語句:.net
Lock l = ...;
l.lock();
try {
// access the resource protected by this lock
} finally {
l.unlock();
}
鎖定和取消鎖定出如今不一樣做用範圍中時,必須謹慎地確保保持鎖定時所執行的全部代碼用 try-finally 或 try-catch 加以保護,以確保在必要時釋放鎖。
Lock
實現提供了使用 synchronized
方法和語句所沒有的其餘功能,包括提供了一個非塊結構的獲取鎖嘗試 (tryLock()
)、一個獲取可中斷鎖的嘗試 (lockInterruptibly()
) 和一個獲取超時失效鎖的嘗試 (tryLock(long, TimeUnit)
)。
Lock
類還能夠提供與隱式監視器鎖徹底不一樣的行爲和語義,如保證排序、非重入用法或死鎖檢測。若是某個實現提供了這樣特殊的語義,則該實現必須對這些語義加以記錄。
注意,Lock
實例只是普通的對象,其自己能夠在 synchronized
代碼塊中做爲目標使用。爲了不混淆,建議除了在其自身的實現中以外,決不要在synchronized代碼塊
中使用 Lock
實例做爲鎖對象。
void |
lock() 獲取鎖。 |
void |
lockInterruptibly() 若是當前線程未被中斷,則獲取鎖。 |
Condition |
newCondition() 返回綁定到此 Lock 實例的新 Condition 實例。 |
boolean |
tryLock() 僅在調用時鎖爲空閒狀態才獲取該鎖。 |
boolean |
tryLock(long time, TimeUnit unit) 若是鎖在給定的等待時間內空閒,而且當前線程未被中斷,則獲取鎖。 |
void |
unlock() 釋放鎖。 |
void lock()
獲取鎖。若是鎖不可用,出於線程調度目的,將禁用當前線程,而且在得到鎖以前,該線程將一直處於休眠狀態。
void lockInterruptibly() throws InterruptedException
若是當前線程未被 中斷,則獲取鎖。
若是鎖可用,則獲取鎖,並當即返回。
若是鎖不可用,出於線程調度目的,將禁用當前線程,而且在發生如下兩種狀況之一之前,該線程將一直處於休眠狀態:
InterruptedException
,並清除當前線程的已中斷狀態。拋出:
InterruptedException
- 若是在獲取鎖時,當前線程被中斷(須要當前線程支持對鎖獲取的中斷)。
boolean tryLock()
僅在調用時鎖爲空閒狀態才獲取該鎖。
若是鎖可用,則獲取鎖,並當即返回值 true
。若是鎖不可用,則此方法將當即返回值 false
。
此方法的典型使用語句以下:
Lock lock = ...;
if (lock.tryLock()) {
try {
// manipulate protected state
} finally {
lock.unlock();
}
} else {
// perform alternative actions
}
此用法可確保若是獲取了鎖,則會釋放鎖,若是未獲取鎖,則不會試圖將其釋放。
返回:
若是獲取了鎖,則返回 true
;不然返回 false
。
boolean tryLock(long time, TimeUnit unit) throws InterruptedException
若是鎖在給定的等待時間內空閒,而且當前線程未被中斷,則獲取鎖。
若是鎖可用,則此方法將當即返回值 true
。
若是鎖不可用,出於線程調度目的,將禁用當前線程,而且在發生如下三種狀況之一前,該線程將一直處於休眠狀態:
true
;InterruptedException
,並會清除當前線程的已中斷狀態;false
。若是 time 小於等於 0,該方法將徹底不等待。參數:
time
- 等待鎖的最長時間
unit
- time
參數的時間單位
返回:
若是在等待時間內得到了鎖,則返回 true
;若是在獲取鎖前超過了等待時間,則返回 false
拋出:
InterruptedException
- 若是在獲取鎖時,當前線程被中斷(須要當前線程支持對鎖獲取的中斷)
void unlock()
釋放鎖。一般只有鎖的保持者能夠釋放它,若是違背了這個限制,可能會拋出(未經檢查的)異常。
Condition newCondition()
返回綁定到此 Lock
實例的新 Condition
實例。
在等待條件前,鎖必須由當前線程保持。調用 Condition.await()
將在等待前以原子方式釋放鎖,並在等待返回前從新獲取鎖。
返回:
用於此 Lock
實例的新 Condition
實例
拋出:
UnsupportedOperationException
- 若是此 Lock
實現不支持條件