3.並發編程-ReentrantLock 細節說明
阿新 • • 發佈:2018-11-20
protect locked interrupt 簡介 數列 條件 printf 操作 這一
2. ReentrantLock-示例 說明
並發編程-ReentrantLock 細節說明
---
title: 並發編程-ReentrantLock 細節說明
date: 2018-07-05 09:06:57
categories:
- 並發編程
---
<Excerpt in index | 首頁摘要>
<!-- more -->
- 本章對ReentrantLock包進行基本介紹,這一章主要對ReentrantLock進行概括性的介紹,內容包括:
- ReentrantLock介紹
- ReentrantLock函數列表
- ReentrantLock示例
<The rest of contents | 余下全文>
並發編程-ReentrantLock介紹 細節說明
1. ReentrantLock-是一個可重入的互斥鎖,又被稱為“獨占鎖”
* ReentrantLock
* ReentrantLock鎖在同一個時間點只能被一個線程鎖持有;而可重入的意思是,ReentrantLock鎖,可以被單個線程多次獲取。
* ReentrantLock分為“公平鎖”和“非公平鎖”。它們的區別體現在獲取鎖的機制上是否公平。“鎖”是為了保護競爭資源,防止多個線程同時操作線程而出錯,ReentrantLock在同一個時間點只能被一個線程獲取(當某線程獲取到“鎖”時,其它線程就必須等待);ReentraantLock是通過一個FIFO的等待隊列來管理獲取該鎖所有線程的。在“公平鎖”的機制下,線程依次排隊獲取鎖;而“非公平鎖”在鎖是可獲取狀態時,不管自己是不是在隊列的開頭都會獲取鎖。
- [x] ReentrantLock 類方法簡介
// 創建一個 ReentrantLock ,默認是“非公平鎖”。 ReentrantLock() // 創建策略是fair的 ReentrantLock。fair為true表示是公平鎖,fair為false表示是非公平鎖。 ReentrantLock(boolean fair) // 查詢當前線程保持此鎖的次數。 int getHoldCount() // 返回目前擁有此鎖的線程,如果此鎖不被任何線程擁有,則返回 null。 protected Thread getOwner() // 返回一個 collection,它包含可能正等待獲取此鎖的線程。 protected Collection<Thread> getQueuedThreads() // 返回正等待獲取此鎖的線程估計數。 int getQueueLength() // 返回一個 collection,它包含可能正在等待與此鎖相關給定條件的那些線程。 protected Collection<Thread> getWaitingThreads(Condition condition) // 返回等待與此鎖相關的給定條件的線程估計數。 int getWaitQueueLength(Condition condition) // 查詢給定線程是否正在等待獲取此鎖。 boolean hasQueuedThread(Thread thread) // 查詢是否有些線程正在等待獲取此鎖。 boolean hasQueuedThreads() // 查詢是否有些線程正在等待與此鎖有關的給定條件。 boolean hasWaiters(Condition condition) // 如果是“公平鎖”返回true,否則返回false。 boolean isFair() // 查詢當前線程是否保持此鎖。 boolean isHeldByCurrentThread() // 查詢此鎖是否由任意線程保持。 boolean isLocked() // 獲取鎖。 void lock() // 如果當前線程未被中斷,則獲取鎖。 void lockInterruptibly() // 返回用來與此 Lock 實例一起使用的 Condition 實例。 Condition newCondition() // 僅在調用時鎖未被另一個線程保持的情況下,才獲取該鎖。 boolean tryLock() // 如果鎖在給定等待時間內沒有被另一個線程保持,且當前線程未被中斷,則獲取該鎖。 boolean tryLock(long timeout, TimeUnit unit) // 試圖釋放此鎖。 void unlock()
2. ReentrantLock-示例 說明
* lock和unlock的作用
import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; // LockTest1.java // 倉庫 class Depot { private int size; // 倉庫的實際數量 private Lock lock; // 獨占鎖 public Depot() { this.size = 0; this.lock = new ReentrantLock(); } public void produce(int val) { lock.lock(); try { size += val; System.out.printf("%s produce(%d) --> size=%d\n", Thread.currentThread().getName(), val, size); } finally { lock.unlock(); } } public void consume(int val) { lock.lock(); try { size -= val; System.out.printf("%s consume(%d) <-- size=%d\n", Thread.currentThread().getName(), val, size); } finally { lock.unlock(); } } }; // 生產者 class Producer { private Depot depot; public Producer(Depot depot) { this.depot = depot; } // 消費產品:新建一個線程向倉庫中生產產品。 public void produce(final int val) { new Thread() { public void run() { depot.produce(val); } }.start(); } } // 消費者 class Customer { private Depot depot; public Customer(Depot depot) { this.depot = depot; } // 消費產品:新建一個線程從倉庫中消費產品。 public void consume(final int val) { new Thread() { public void run() { depot.consume(val); } }.start(); } } public class LockTest1 { public static void main(String[] args) { Depot mDepot = new Depot(); Producer mPro = new Producer(mDepot); Customer mCus = new Customer(mDepot); mPro.produce(60); mPro.produce(120); mCus.consume(90); mCus.consume(150); mPro.produce(110); } }
運行結果
Thread-0 produce( 60) --> left= 0, inc= 60, size= 60 Thread-1 produce(120) --> left= 80, inc= 40, size=100 Thread-2 consume( 90) <-- left= 0, dec= 90, size= 10 Thread-3 consume(150) <-- left=140, dec= 10, size= 0 Thread-4 produce(110) --> left= 10, inc=100, size=100 Thread-3 consume(150) <-- left= 40, dec=100, size= 0 Thread-4 produce(110) --> left= 0, inc= 10, size= 10 Thread-3 consume(150) <-- left= 30, dec= 10, size= 0 Thread-1 produce(120) --> left= 0, inc= 80, size= 80 Thread-3 consume(150) <-- left= 0, dec= 30, size= 50
3.並發編程-ReentrantLock 細節說明