2010-05-18 102 views
4

我有兩個線程。第一個是這樣的:互斥鎖需要很長時間才能解鎖

while(1) 
{ 
    pthread_mutex_lock(&mutex); 
    //DO WORK 
    pthread_mutex_unlock(&mutex); 
    pthread_yield(); 
} 

第二個鎖定用戶事件互斥,更改某些設置和解鎖。線程一秒~200次迭代。但有時需要第二個線程長達3秒才能激活(鎖定互斥鎖)。我如何確保更快的響應?

編輯 - 第二線程:

while(1) 
{ 
    waitForUserInput(); // blocking call to linux input 
    pthread_mutex_lock(&mutex); 
    // Change some settings which are used by the first thread 
    pthread_mutex_unlock(&mutex); 
} 

EDIT2 - 修正的問題( 「解鎖互斥」 - > 「鎖定互斥」)。

+0

你能告訴我們第二個線程是什麼樣子嗎? – luke 2010-05-18 23:25:14

+0

你的意思是第二個線程需要3秒才能獲取互斥鎖或釋放互斥鎖? – Jay 2010-05-19 13:22:18

+0

我的意思是第二個線程獲取互斥量需要3秒(並非總是)。因此,它一段時間沒有反應。 – 2010-05-20 00:26:40

回答

1

地把控制給其他線程嘗試改變pthread_yield()usleep(10)usleep(100)來確定產量導致您的問題,因爲我已經看到情況下,yield沒有任何作用,這會導致你的循環解鎖並且重新鎖定太快,以致第一個線程大部分時間都無法捕獲它的鎖。那麼你可以考慮在pthread中查看條件變量,如果你想要更多的控制。

1

我總是很擔心,當我看到pthread_yield根據man page它是非標準的,所以我通常避免它也真的沒有給你任何保證,它會讓你在運行隊列的後面,但那doesn這並不意味着其他任何東西都會運行,這取決於操作系統如何優先處理您的線程。

你可能想要做的是明確使用條件變量signalwait

1

您的設計很糟糕。一個線程只有在需要訪問共享數據結構時才能擁有互斥鎖。這應該是線程運行時間的一小部分,而不是絕大多數。如果你看到了你正在開發的模式,現在是重新設計的時候了。

一種可能的模式是讓計算線程在不保持互斥鎖的情況下運行時持有指向全局數據的指針。然後,UI線程可以基於UI輸入創建新版本的全局數據,然後將指針發佈到新數據,以便計算線程在下次獲取指針時看到它。這樣,只要需要複製指針,計算線程就只需保存互斥鎖。

下面是計算線程的過於簡單化的佈局:

pthread_mutex_lock(&mutex); 
my_pointer = shared_pointer; 
pthread_mutex_unlock(&mutex); 
do_calculations(); 

而對於UI線程,邏輯是這樣的:你修改數據的副本。您製作一份新的數據副本。你獲得互斥體。您將shared_pointer更改爲指向數據的兩個副本中的一個。您持有另一份副本以在下一個通行證中修改。