溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點(diǎn)擊 登錄注冊 即表示同意《億速云用戶服務(wù)條款》

Binary Semaphore和Reentrant Lock的區(qū)別有哪些

發(fā)布時間:2021-10-20 09:11:22 來源:億速云 閱讀:261 作者:iii 欄目:web開發(fā)

這篇文章主要講解了“Binary Semaphore和Reentrant Lock的區(qū)別有哪些”,文中的講解內(nèi)容簡單清晰,易于學(xué)習(xí)與理解,下面請大家跟著小編的思路慢慢深入,一起來研究和學(xué)習(xí)“Binary Semaphore和Reentrant Lock的區(qū)別有哪些”吧!

1. 引言

探討二進(jìn)制信號量(Binary Semaphore)和可重入鎖(Reentrant  Lock)。

2. 什么是二進(jìn)制信號量

二進(jìn)制信號量在單個資源的訪問上提供信令機(jī)制。換句話說,二進(jìn)制信號量提供了一種互斥機(jī)制,一次只允許一個線程訪問一個關(guān)鍵部分。它只保留一個通行證,因此二進(jìn)制信號量只有兩種狀態(tài):可用(count=1)  和不可用(count=0)。

我們使用Java中的 Semaphore 類來討論一個簡單的二進(jìn)制信號量的實(shí)現(xiàn) :

Semaphore binarySemaphore = new Semaphore(1); try {     binarySemaphore.acquire();     assertEquals(0, binarySemaphore.availablePermits()); } catch (InterruptedException e) {     e.printStackTrace(); } finally {     binarySemaphore.release();     assertEquals(1, binarySemaphore.availablePermits()); }

在這里,我們可以觀察到,acquire方法將可用許可減少了一個。類似地,release方法將可用許可增加1。

另外,Semaphore 類提供了 fairness 參數(shù)。當(dāng)設(shè)置為true時,fairness  參數(shù)確保請求線程獲取許可的順序(基于它們的等待時間):

Semaphore binarySemaphore = new Semaphore(1, true);

3. 什么是重入鎖?

可重入鎖是一種互斥機(jī)制,允許線程在沒有死鎖的情況下(多次)重入資源上的鎖。

進(jìn)入鎖的線程每次增加一個持有計數(shù)。類似地,請求解鎖時持有計數(shù)減少。因此,資源被鎖定,直到計數(shù)器返回到零。例如,讓我們看一個使用Java中  ReentrantLock 類的簡單實(shí)現(xiàn):

ReentrantLock reentrantLock = new ReentrantLock(); try {     reentrantLock.lock();     assertEquals(1, reentrantLock.getHoldCount());     assertEquals(true, reentrantLock.isLocked()); } finally {     reentrantLock.unlock();     assertEquals(0, reentrantLock.getHoldCount());     assertEquals(false, reentrantLock.isLocked()); }

這里,lock方法將持有計數(shù)增加1,并鎖定資源。類似地,unlock方法減少持有計數(shù),如果持有計數(shù)為零,則解鎖資源。當(dāng)線程重新進(jìn)入鎖時,它必須請求相同次數(shù)的解鎖以釋放資源:

reentrantLock.lock(); reentrantLock.lock(); assertEquals(2, reentrantLock.getHoldCount()); assertEquals(true, reentrantLock.isLocked());  reentrantLock.unlock(); assertEquals(1, reentrantLock.getHoldCount()); assertEquals(true, reentrantLock.isLocked());  reentrantLock.unlock(); assertEquals(0, reentrantLock.getHoldCount()); assertEquals(false, reentrantLock.isLocked());

與Semaphore類類似,ReentrantLock類也支持 fairness 參數(shù):

ReentrantLock reentrantLock = new ReentrantLock(true);

4. 二進(jìn)制信號量與重入鎖

4.1. 機(jī)制

二進(jìn)制信號量是一種信令機(jī)制,而可重入鎖是一種鎖定機(jī)制。

4.2.所有權(quán)

沒有線程是二進(jìn)制信號量的所有者。但是,成功鎖定資源的最后一個線程是可重入鎖的所有者。

4.3. 本質(zhì)

二進(jìn)制信號量本質(zhì)上是不可重入的,這意味著同一個線程不能重新獲取關(guān)鍵部分,否則會導(dǎo)致死鎖。另一方面,可重入鎖本質(zhì)上允許同一線程多次重入鎖。

4.4. 靈活性

二進(jìn)制信號量通過允許鎖定機(jī)制和死鎖恢復(fù)的自定義實(shí)現(xiàn),提供了更高級別的同步機(jī)制。因此,它為開發(fā)人員提供了更多的控制。然而,可重入鎖則是一種低級同步,具有固定的鎖機(jī)制。

4.5. 可修改性

二進(jìn)制信號量支持 wait 和  signal(在Java的Semaphore類中獲取和釋放)等操作,以允許任何進(jìn)程修改可用的許可證。另一方面,只有鎖定/解鎖資源的同一線程才能修改可重入鎖。

4.6. 死鎖恢復(fù)

二進(jìn)制信號量提供了一種非所有權(quán)釋放機(jī)制。因此,任何線程都可以釋放二進(jìn)制信號量的死鎖恢復(fù)許可。

相反,在重入鎖的情況下很難實(shí)現(xiàn)死鎖恢復(fù)。例如,如果可重入鎖的所有者線程進(jìn)入睡眠或無限等待狀態(tài),就不可能釋放資源,從而導(dǎo)致死鎖情況。

感謝各位的閱讀,以上就是“Binary Semaphore和Reentrant Lock的區(qū)別有哪些”的內(nèi)容了,經(jīng)過本文的學(xué)習(xí)后,相信大家對Binary Semaphore和Reentrant Lock的區(qū)別有哪些這一問題有了更深刻的體會,具體使用情況還需要大家實(shí)踐驗證。這里是億速云,小編將為大家推送更多相關(guān)知識點(diǎn)的文章,歡迎關(guān)注!

向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報,并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI