執行緒同步之互斥量

2022-08-17 02:48:14 字數 1642 閱讀 4739

互斥量:

當多個執行緒共享相同的記憶體時,需要每乙個執行緒看到相同的檢視。當乙個執行緒修改變數時,而其他執行緒也可以讀取或者修改這個變數,就需要對這些執行緒同步,確保他們不會訪問到無效的變數

在變數修改時間多於乙個儲存器訪問週期的處理器結構中,當儲存器的讀和寫這兩個週期交叉時,這種潛在的不一致性就會出現。當然這與處理器相關,但是在可移植的程式中並不能對處理器做出任何假設

為了讓執行緒訪問資料不產生衝突,這要就需要對變數加鎖,使得同一時刻只有乙個執行緒可以訪問變數。互斥量本質就是鎖,訪問共享資源前對互斥量加鎖,訪問完成後解鎖

當互斥量加鎖以後,其他所有需要訪問該互斥量的執行緒都將阻塞

當互斥量解鎖以後,所有因為這個互斥量阻塞的執行緒都將變為就緒態,第乙個獲得cpu的執行緒會獲得互斥量,變為執行態,而其他執行緒會繼續變為阻塞,在這種方式下訪問互斥量每次只有乙個執行緒能向前執行

互斥量用pthread_mutex_t型別的資料表示,在使用之前需要對互斥量初始化

1、如果是動態分配的互斥量,可以呼叫pthread_mutex_init()函式初始化

2、如果是靜態分配的互斥量,還可以把它置為常量pthread_mutex_initializer

3、動態分配的互斥量在釋放記憶體之前需要呼叫pthread_mutex_destroy()

int pthread_mutex_init(pthread_mutex_t *restrict mutex,

const pthread_mutexattr_t *restrict attr);

int pthread_mutex_destroy(pthread_mutex_t *mutex);

pthread_mutex_t mutex = pthread_mutex_initializer;

加鎖 int pthread_mutex_lock(pthread_mutex_t *mutex); 

成功返回0,失敗返回錯誤碼。如果互斥量已經被鎖住,那麼會導致該執行緒阻塞

int pthread_mutex_trylock(pthread_mutex_t *mutex);

成功返回0,失敗返回錯誤碼。如果互斥量已經被鎖住,不會導致執行緒阻塞

解鎖  

int pthread_mutex_unlock(pthread_mutex_t *mutex);

成功返回0,失敗返回錯誤碼。如果乙個互斥量沒有被鎖住,那麼解鎖就會出錯

死鎖:執行緒一直在等待鎖,而鎖卻無法解開

如果乙個執行緒對已經占有的互斥量繼續加鎖,那麼他就會陷入死鎖狀態。

lock mutex--------lock mutex--------阻塞

解除阻塞狀態的條件:mutex unlock

mutex unlock的條件:  解除阻塞態

程式中使用多個互斥量時,如果乙個執行緒一直占有互斥量a,並且試圖加鎖互斥量b,但是擁有互斥量b的執行緒卻要加鎖互斥量a,這時就會出現死鎖

執行緒1: lock a成功

執行緒2 : lock b成功 

執行緒1: lock b失敗, 阻塞

執行緒2: lock a失敗, 阻塞

執行緒1解除阻塞的條件:執行緒2將b解鎖

執行緒2解除阻塞的條件:執行緒1將a解鎖

如何去避免

你可以小心的控制互斥量加鎖的順序來避免死鎖,例如所有的執行緒都在加鎖b之前先加鎖a,那麼這兩個互斥量就不會產生死鎖了

執行緒同步之互斥量Mutex

前面的文章介紹了執行緒的建立 終止 連線和分離。本篇介紹執行緒的同步。多執行緒的難點是對共享資源的訪問,如何保證多個執行緒能夠 同時 訪問同乙個共享資源而又不引起衝突,就是執行緒同步的本質。互斥量用來確保共享資源同時只被乙個執行緒訪問。互斥量有兩種狀態 已鎖定 locked 和未鎖定 unlocke...

執行緒同步 互斥量

下面以乙個簡單的多執行緒程式來演示如何使用互斥量來進行執行緒同步。在主線程中,我們建立子執行緒,並把陣列msg作為引數傳遞給子執行緒,然後主線程呼叫函式pthread mutex lock對互斥量加鎖,等待輸入,輸入完成後,呼叫函式pthread mutex unlock對互斥量解鎖,從而使執行緒函...

執行緒同步 互斥量

互斥量的使用 執行緒同步之互斥量 include include include include include include include using namespace std 全域性變數,兩個執行緒都可以修改,因此修改的時候需要加鎖 int g value 0 互斥量 pthread mu...