關於pthread_cond_signal與pthread_cond_broadcast的使用...

       在code review中,我會發現不少人喜歡在pthread_mutex_lock()和pthread_mutex_unlock(()之間調用 pthread_cond_signal或者pthread_cond_broadcast函數,從邏輯上來講,這種使用方法是徹底正確的。可是在多線程環境中,這種使用方法多是低效的。posix1標準說,pthread_cond_signal與pthread_cond_broadcast無需考慮調用線程是不是mutex的擁有者,也就是說,能夠在lock與unlock之外的區域調用。若是咱們對調用行爲不關心,那麼請在lock區域以外調用吧。這裏舉個例子:
      
咱們假設系統中有線程1和線程2,他們都想獲取mutex後處理共享數據,再釋放mutex。請看這種序列:
      
1)線程1獲取mutex,在進行數據處理的時候,線程2也想獲取mutex,可是此時被線程1所佔用,線程2進入休眠,等待mutex被釋放。
      
2)線程1作完數據處理後,調用pthread_cond_signal()喚醒等待隊列中某個線程,在本例中也就是線程2。線程1在調用pthread_mutex_unlock()前,由於系統調度的緣由,線程2獲取使用CPU的權利,那麼它就想要開始處理數據,可是在開始處理以前,mutex必須被獲取,很遺憾,線程1正在使用mutex,因此線程2被迫再次進入休眠。
       
3)而後就是線程1執行pthread_mutex_unlock()後,線程2方能被再次喚醒。
       從這裏看,使用的效率是比較低的,若是再多線程環境中,這種狀況頻繁發生的話,是一件比較痛苦的事情。因此以爲,若是程序不關心線程可預知的調度行爲,那麼最好在鎖定區域之外調用他們。 php

對於
int pthread_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex);
int pthread_cond_timedwait(pthread_cond_t *cond, pthread_mutex_t *mutex, const struct timespec *abstime);
,必定要在mutex的鎖定區域內使用。
若是要正確的使用pthread_mutex_lock與pthread_mutex_unlock,請參考
pthread_cleanup_push 和pthread_cleanup_pop宏,它可以在線程被cancel的時候正確的釋放mutex! html

        pthread_cond_wait()  用於阻塞當前線程,等待別的線程使用 pthread_cond_signal() pthread_cond_broadcast來喚醒它  pthread_cond_wait()   必須與pthread_mutex 配套使用。 pthread_cond_wait() 函數一進入wait狀態就會自動release mutex。當其餘線程經過 pthread_cond_signal() pthread_cond_broadcast ,把該線程喚醒,使 pthread_cond_wait()經過(返回)時,該線程又自動得到該 mutex
        pthread_cond_signal 函數的做用是發送一個信號給另一個正在處於阻塞等待狀態的線程,使其脫離阻塞狀態,繼續執行.若是沒有線程處在阻塞等待狀態,pthread_cond_signal也會成功返回。
        使用pthread_cond_signal通常不會有「驚羣現象」產生,他最多隻給一個線程發信號。假若有多個線程正在阻塞等待着這個條件變量的話,那麼是根據各等待線程優先級的高低肯定哪一個線程接收到信號開始繼續執行。若是各線程優先級相同,則根據等待時間的長短來肯定哪一個線程得到信號。但不管如何一個pthread_cond_signal調用最多發信一次。
        可是 pthread_cond_signal 在多處理器上可能同時喚醒多個線程,當你只能讓一個線程處理某個任務時,其它被喚醒的線程就須要繼續 wait,並且規範要求 pthread_cond_signal 至少喚醒一個pthread_cond_wait上的線程,其實有些實現爲了簡單在單處理器上也會喚醒多個線程. 
        另外,某些應用,如線程池, pthread_cond_broadcast 喚醒所有線程,但咱們一般只須要一部分線程去作執行任務,因此其它的線程須要繼續wait.
 
http://apps.hi.baidu.com/share/detail/19786281
相關文章
相關標籤/搜索