ReentrantLock是Java併發包中一個很是有用的組件,一些併發集合類也是用ReentrantLock實現,包括ConcurrentHashMap。ReentrantLock具備三個特性:等待可中斷、可實現公平鎖、以及鎖能夠綁定多個條件。html
ReentrantLock與synchronized關鍵字同樣,屬於互斥鎖,synchronized中的鎖是非公平的(公平鎖是指多個線程等待同一個鎖時,必須按照申請鎖的時間順序來依次得到鎖),ReentrantLock默認狀況下也是非公平的,但能夠經過帶布爾值的構造函數要求使用公平鎖。線程經過ReentrantLock的lock()方法得到鎖,用unlock()方法釋放鎖。java
ReentrantLock在等待鎖時可使用lockInterruptibly()方法選擇中斷, 改成處理其餘事情,而synchronized關鍵字,線程須要一直等待下去。一樣的,tryLock()方法能夠設置超時時間,用於在超時時間內一直獲取不到鎖時進行中斷。併發
ReentrantLock能夠實現公平鎖,而synchronized的鎖是非公平的。ide
ReentrantLock擁有方便的方法用於獲取正在等待鎖的線程。函數
ReentrantLock能夠同時綁定多個Condition對象,而synchronized中,鎖對象的wait()和notify()或notifyAll()方法能夠實現一個隱含的條件,若是要和多於一個條件關聯時,只能再加一個額外的鎖,而ReentrantLock只須要屢次調用newCondition方法便可。性能
在JDK1.6以前,ReentrantLock的性能要明顯優於synchronized,可是JDK1.6中加入了不少針對鎖的優化措施,synchronized和ReentrantLock的性能基本徹底持平了。優化
ReentrantLock的主要缺點是方法須要置於try-finally塊中,另外,開發人員須要負責獲取和釋放鎖,而開發人員經常忘記在finally中釋放鎖。線程
import java.util.concurrent.locks.ReentrantLock; import java.util.logging.Level; import java.util.logging.Logger; /** * Java program to show, how to use ReentrantLock in Java. * Reentrant lock is an alternative way of locking * apart from implicit locking provided by synchronized keyword in Java. * * @author Javin Paul */ public class ReentrantLockHowto { private final ReentrantLock lock = new ReentrantLock(); private int count = 0; //Locking using Lock and ReentrantLock public int getCount() { lock.lock(); try { System.out.println(Thread.currentThread().getName() + " gets Count: " + count); return count++; } finally { lock.unlock(); } } //Implicit locking using synchronized keyword public synchronized int getCountTwo() { return count++; } public static void main(String args[]) { final ThreadTest counter = new ThreadTest(); Thread t1 = new Thread() { @Override public void run() { while (counter.getCount() < 6) { try { Thread.sleep(100); } catch (InterruptedException ex) { ex.printStackTrace(); } } } }; Thread t2 = new Thread() { @Override public void run() { while (counter.getCount() < 6) { try { Thread.sleep(100); } catch (InterruptedException ex) { ex.printStackTrace(); } } } }; t1.start(); t2.start(); } } Output: Thread-0 gets Count: 0 Thread-1 gets Count: 1 Thread-1 gets Count: 2 Thread-0 gets Count: 3 Thread-1 gets Count: 4 Thread-0 gets Count: 5 Thread-0 gets Count: 6 Thread-1 gets Count: 7
Read more: http://javarevisited.blogspot...code