首頁(yè) 常見(jiàn)問(wèn)題 正文
聚名企服

信號(hào)量和互斥量的區(qū)別是什么?

轉(zhuǎn)載 chaicp 2021-11-17 17:43:32 5715
本教程操作環(huán)境:windows7系統(tǒng)、Dell G3電腦。互斥量和信號(hào)量的區(qū)別1. 互斥量用于線程的互斥,信號(hào)量用于線程的同步。這是互斥量和信號(hào)量的根本區(qū)別

本教程操作環(huán)境:windows7系統(tǒng)、Dell G3電腦。

互斥量和信號(hào)量的區(qū)別

1. 互斥量用于線程的互斥,信號(hào)量用于線程的同步。

這是互斥量和信號(hào)量的根本區(qū)別,也就是互斥和同步之間的區(qū)別。

互斥:是指某一資源同時(shí)只允許一個(gè)訪問(wèn)者對(duì)其進(jìn)行訪問(wèn),具有唯一性和排它性。但互斥無(wú)法限制訪問(wèn)者對(duì)資源的訪問(wèn)順序,即訪問(wèn)是無(wú)序的。

同步:是指在互斥的基礎(chǔ)上(大多數(shù)情況),通過(guò)其它機(jī)制實(shí)現(xiàn)訪問(wèn)者對(duì)資源的有序訪問(wèn)。在大多數(shù)情況下,同步已經(jīng)實(shí)現(xiàn)了互斥,特別是所有寫(xiě)入資源的情況必定是互斥的。少數(shù)情況是指可以允許多個(gè)訪問(wèn)者同時(shí)訪問(wèn)資源

2. 互斥量值只能為0/1,信號(hào)量值可以為非負(fù)整數(shù)。

也就是說(shuō),一個(gè)互斥量只能用于一個(gè)資源的互斥訪問(wèn),它不能實(shí)現(xiàn)多個(gè)資源的多線程互斥問(wèn)題。信號(hào)量可以實(shí)現(xiàn)多個(gè)同類(lèi)資源的多線程互斥和同步。當(dāng)信號(hào)量為單值信號(hào)量是,也可以完成一個(gè)資源的互斥訪問(wèn)。

3. 互斥量的加鎖和解鎖必須由同一線程分別對(duì)應(yīng)使用,信號(hào)量可以由一個(gè)線程釋放,另一個(gè)線程得到。

互斥量(Mutex)

互斥量表現(xiàn)互斥現(xiàn)象的數(shù)據(jù)結(jié)構(gòu),也被當(dāng)作二元信號(hào)燈。一個(gè)互斥基本上是一個(gè)多任務(wù)敏感的二元信號(hào),它能用作同步多任務(wù)的行為,它常用作保護(hù)從中斷來(lái)的臨界段代碼并且在共享同步使用的資源。

 

Mutex本質(zhì)上說(shuō)就是一把鎖,提供對(duì)資源的獨(dú)占訪問(wèn),所以Mutex主要的作用是用于互斥。Mutex對(duì)象的值,只有0和1兩個(gè)值。這兩個(gè)值也分別代表了Mutex的兩種狀態(tài)。值為0, 表示鎖定狀態(tài),當(dāng)前對(duì)象被鎖定,用戶進(jìn)程/線程如果試圖Lock臨界資源,則進(jìn)入排隊(duì)等待;值為1,表示空閑狀態(tài),當(dāng)前對(duì)象為空閑,用戶進(jìn)程/線程可以Lock臨界資源,之后Mutex值減1變?yōu)?。

Mutex可以被抽象為四個(gè)操作:

- 創(chuàng)建 Create

- 加鎖 Lock

- 解鎖 Unlock

- 銷(xiāo)毀 Destroy

Mutex被創(chuàng)建時(shí)可以有初始值,表示Mutex被創(chuàng)建后,是鎖定狀態(tài)還是空閑狀態(tài)。在同一個(gè)線程中,為了防止死鎖,系統(tǒng)不允許連續(xù)兩次對(duì)Mutex加鎖(系統(tǒng)一般會(huì)在第二次調(diào)用立刻返回)。也就是說(shuō),加鎖和解鎖這兩個(gè)對(duì)應(yīng)的操作,需要在同一個(gè)線程中完成。

不同操作系統(tǒng)中提供的Mutex函數(shù):

動(dòng)作/系統(tǒng)

Win32

Linyx

Solaris

創(chuàng)建

CreateMutex

pthread_mutex_init

mutex_init

加鎖

WaitForSingleObject

pthread_mutex_lock

mutex_lock

解鎖

ReleaseMutex

pthread_mutex_unlock

mutex_unlock

銷(xiāo)毀

CloseHandle

pthread_mutex_destroy

mutex_destroy

死鎖主要發(fā)生在有多個(gè)依賴(lài)鎖存在時(shí), 會(huì)在一個(gè)線程試圖以與另一個(gè)線程相反順序鎖住互斥量時(shí)發(fā)生. 如何避免死鎖是使用互斥量應(yīng)該格外注意的東西。

  總體來(lái)講, 有幾個(gè)不成文的基本原則:

  對(duì)共享資源操作前一定要獲得鎖。

  完成操作以后一定要釋放鎖。

  盡量短時(shí)間地占用鎖。

  如果有多鎖, 如獲得順序是ABC連環(huán)扣, 釋放順序也應(yīng)該是ABC。

  線程錯(cuò)誤返回時(shí)應(yīng)該釋放它所獲得的鎖。

也許還有讀者好奇,“掛起等待”和“喚醒等待線程”的操作如何實(shí)現(xiàn)?每個(gè)Mutex有一個(gè)等待隊(duì)列,一個(gè)線程要在Mutex上掛起等待,首先在把自己加入等待隊(duì)列中,然后置線程狀態(tài)為睡眠,然后調(diào)用調(diào)度器函數(shù)切換到別的線程。一個(gè)線程要喚醒等待隊(duì)列中的其它線程,只需從等待隊(duì)列中取出一項(xiàng),把它的狀態(tài)從睡眠改為就緒,加入就緒隊(duì)列,那么下次調(diào)度器函數(shù)執(zhí)行時(shí)就有可能切換到被喚醒的線程。

一般情況下,如果同一個(gè)線程先后兩次調(diào)用lock,在第二次調(diào)用時(shí),由于鎖已經(jīng)被占用,該線程會(huì)掛起等待別的線程釋放鎖,然而鎖正是被自己占用著的,該線程又被掛起而沒(méi)有機(jī)會(huì)釋放鎖,因此就永遠(yuǎn)處于掛起等待狀態(tài)了,這叫做死鎖(Deadlock)。另一種典型的死鎖情形是這樣:線程A獲得了鎖1,線程B獲得了鎖2,這時(shí)線程A調(diào)用lock試圖獲得鎖2,結(jié)果是需要掛起等待線程B釋放鎖2,而這時(shí)線程B也調(diào)用lock試圖獲得鎖1,結(jié)果是需要掛起等待線程A釋放鎖1,于是線程A和B都永遠(yuǎn)處于掛起狀態(tài)了。不難想象,如果涉及到更多的線程和更多的鎖,有沒(méi)有可能死鎖的問(wèn)題將會(huì)變得復(fù)雜和難以判斷。

信號(hào)量

信號(hào)量(Semaphore),有時(shí)被稱(chēng)為信號(hào)燈,是在多線程環(huán)境下使用的一種設(shè)施, 它負(fù)責(zé)協(xié)調(diào)各個(gè)線程, 以保證它們能夠正確、合理的使用公共資源。

信號(hào)量可以分為幾類(lèi):

二進(jìn)制信號(hào)量(binary semaphore):只允許信號(hào)量取0或1值,其同時(shí)只能被一個(gè)線程獲取。

整型信號(hào)量(integer semaphore):信號(hào)量取值是整數(shù),它可以被多個(gè)線程同時(shí)獲得,直到信號(hào)量的值變?yōu)?。

記錄型信號(hào)量(record semaphore):每個(gè)信號(hào)量s除一個(gè)整數(shù)值value(計(jì)數(shù))外,還有一個(gè)等待隊(duì)列List,其中是阻塞在該信號(hào)量的各個(gè)線程的標(biāo)識(shí)。當(dāng)信號(hào)量被釋放一個(gè),值被加一后,系統(tǒng)自動(dòng)從等待隊(duì)列中喚醒一個(gè)等待中的線程,讓其獲得信號(hào)量,同時(shí)信號(hào)量再減一。

信號(hào)量通過(guò)一個(gè)計(jì)數(shù)器控制對(duì)共享資源的訪問(wèn),信號(hào)量的值是一個(gè)非負(fù)整數(shù),所有通過(guò)它的線程都會(huì)將該整數(shù)減一。如果計(jì)數(shù)器大于0,則訪問(wèn)被允許,計(jì)數(shù)器減1;如果為0,則訪問(wèn)被禁止,所有試圖通過(guò)它的線程都將處于等待狀態(tài)。

計(jì)數(shù)器計(jì)算的結(jié)果是允許訪問(wèn)共享資源的通行證。因此,為了訪問(wèn)共享資源,線程必須從信號(hào)量得到通行證, 如果該信號(hào)量的計(jì)數(shù)大于0,則此線程獲得一個(gè)通行證,這將導(dǎo)致信號(hào)量的計(jì)數(shù)遞減,否則,此線程將阻塞直到獲得一個(gè)通行證為止。當(dāng)此線程不再需要訪問(wèn)共享資源時(shí),它釋放該通行證,這導(dǎo)致信號(hào)量的計(jì)數(shù)遞增,如果另一個(gè)線程等待通行證,則那個(gè)線程將在那時(shí)獲得通行證。

Semaphore可以被抽象為五個(gè)操作:

- 創(chuàng)建 Create

- 等待 Wait:

線程等待信號(hào)量,如果值大于0,則獲得,值減一;如果只等于0,則一直線程進(jìn)入睡眠狀態(tài),知道信號(hào)量值大于0或者超時(shí)。

-釋放 Post

執(zhí)行釋放信號(hào)量,則值加一;如果此時(shí)有正在等待的線程,則喚醒該線程。

-試圖等待 TryWait

如果調(diào)用TryWait,線程并不真正的去獲得信號(hào)量,還是檢查信號(hào)量是否能夠被獲得,如果信號(hào)量值大于0,則TryWait返回成功;否則返回失敗。

-銷(xiāo)毀 Destroy

信號(hào)量,是可以用來(lái)保護(hù)兩個(gè)或多個(gè)關(guān)鍵代碼段,這些關(guān)鍵代碼段不能并發(fā)調(diào)用。在進(jìn)入一個(gè)關(guān)鍵代碼段之前,線程必須獲取一個(gè)信號(hào)量。如果關(guān)鍵代碼段中沒(méi)有任何線程,那么線程會(huì)立即進(jìn)入該框圖中的那個(gè)部分。一旦該關(guān)鍵代碼段完成了,那么該線程必須釋放信號(hào)量。其它想進(jìn)入該關(guān)鍵代碼段的線程必須等待直到第一個(gè)線程釋放信號(hào)量。為了完成這個(gè)過(guò)程,需要?jiǎng)?chuàng)建一個(gè)信號(hào)量,然后將Acquire Semaphore VI以及Release Semaphore VI分別放置在每個(gè)關(guān)鍵代碼段的首末端。確認(rèn)這些信號(hào)量VI引用的是初始創(chuàng)建的信號(hào)量。

動(dòng)作/系統(tǒng)

Win32

POSIX

創(chuàng)建

CreateSemaphore

sem_init

等待

WaitForSingleObject

sem _wait

釋放

ReleaseMutex

sem _post

試圖等待

WaitForSingleObject

sem _trywait

銷(xiāo)毀

CloseHandle

sem_destroy

聲明:本文轉(zhuǎn)載于:互聯(lián)網(wǎng),如有侵犯,請(qǐng)聯(lián)系service@Juming.com刪除
相關(guān)標(biāo)簽: 信號(hào)量和互斥量

編輯推薦

  • 域名注冊(cè)專(zhuān)題合集 域名注冊(cè)專(zhuān)題合集

  • 域名搶注專(zhuān)題合集 域名搶注專(zhuān)題合集

  • 企業(yè)建站專(zhuān)題合集 企業(yè)建站專(zhuān)題合集

主站蜘蛛池模板: 东京热无码一区二区三区av| 国产精品成人无码久久久久久 | 国产精品一区二区久久精品无码| 国产乱人伦无无码视频试看| 亚洲无码在线播放| 国产仑乱无码内谢| 久久久无码人妻精品无码| 无码喷水一区二区浪潮AV | 宅男在线国产精品无码| 无码一区二区三区视频| 亚洲av永久中文无码精品| 亚洲AV无码乱码在线观看牲色| 午夜亚洲AV日韩AV无码大全 | 日韩精品无码一区二区三区四区 | 亚洲人成无码网站| 一本天堂ⅴ无码亚洲道久久| 国产精品无码DVD在线观看| 未满小14洗澡无码视频网站| 亚洲精品无码av天堂| 97碰碰碰人妻视频无码| 亚洲国产精品成人精品无码区在线| av中文无码乱人伦在线观看| 精品三级AV无码一区| 人妻精品久久无码专区精东影业| 亚洲人成无码久久电影网站| 亚洲精品无码mⅴ在线观看| 日韩丰满少妇无码内射| 内射人妻少妇无码一本一道| 国产成人综合日韩精品无码| 中文无码一区二区不卡αv| 亚洲中文字幕无码不卡电影| 韩国无码AV片在线观看网站| 久久久无码精品亚洲日韩蜜臀浪潮| 人妻中文字幕AV无码专区| 亚洲欧洲AV无码专区| 用舌头去添高潮无码视频 | 亚洲乱人伦中文字幕无码| 亚洲性无码AV中文字幕| 久热中文字幕无码视频| 亚洲AV无码久久久久网站蜜桃| 少妇无码AV无码专区在线观看|