條件變數(一)

2022-08-16 00:30:23 字數 917 閱讀 4484

互斥器mutex用來排他性的訪問共享資料,他不是等待原語。若要等待某個條件成立,我們應該使用條件變數(condition variable)。條件變數顧名思義就是乙個或多個執行緒等待某個布林表示式為真,即等待別的執行緒喚醒它。

條件變數只有一種使用方式,wait端:

1、必須與mutex一起使用,以保護布林表示式的讀寫收到保護。

2、mutex上鎖後才能呼叫wait()等待。

3、把wait()放到 while迴圈內,而不是if語句塊內。否則會導致假喚醒。

對於條件變數,我的簡單理解就是消費者和生產者:notify一段為生產者,告訴wait端有元素可以消費了。我在專案中最長遇到的就是將其用到blockingqueue中。下面是簡單的實現:

生產者, 將元素去出佇列:

1

void

enqueue(t t)

2

消費者,將t value放入佇列:

1 t dequeue(t &value)

27 value =q.front();

8q.pop();

9return

value;

10 }

第五行**c.wait()會把執行緒投入睡眠,並釋放執行緒持有的互斥鎖,當wait()返回時,該再次上鎖,該執行緒再次持有該互斥鎖。(這個怎麼做到的?釋放互斥鎖,然後睡眠期間,該鎖不會被別的執行緒持有嗎?)

注意:一定要使用迴圈判斷queue是否有元素可用,才調能用c.wait()。不然可能產生假喚醒。因為notify_one(呼叫的是pthread_cond_signal)或者notify_all(呼叫的是pthread_cond_broadcast)都只能喚醒正在wait()的執行緒,這就是所謂的邊沿觸發。 

注:本文參考

POSIX執行緒 條件變數(一)

為什麼使用條件變數 condition variable 想想我們怎麼實現下面的場景 當執行緒a需要通知執行緒b某件事情已經準備好,我們該怎麼做?我們通常的做法是 設定乙個全域性變數v,如果執行緒a已經準備好了某件事,則把v設定為1 執行緒b則不停得檢測v,直到v變為1再繼續下面的操作。這種做法的缺...

條件變數 pthread cond init

include int pthread cond init pthread cond t cv,const pthread condattr t cattr 返回值 函式成功返回0 任何其他返回值都表示錯誤初始化乙個條件變數。當引數cattr為空指標時,函式建立的是乙個預設的條件變數。否則條件變數的...

條件變數 pthread cond init

include int pthread cond init pthread cond t cv,const pthread condattr t cattr 返回值 函式成功返回0 任何其他返回值都表示錯誤初始化乙個條件變數。當引數cattr為空指標時,函式建立的是乙個預設的條件變數。否則條件變數的...