2012-04-09 57 views
4

我繼承像這樣的代碼:調用ResetEvent()時,我需要互斥鎖嗎?

m_mutex.Lock(); 
ResetEvent(m_hSyncObject); 
m_mutex.Unlock(); 

同爲SetEvent()

在這種情況下必要的互斥體 - 做這些電話循規蹈矩或者我可以卸下鎖脫身?這個函數已經有了一些我曾經提出過的原子的值,現在只是這些事件在鎖定之內,所以如果可能的話,去掉它們將是一個很大的勝利。

+2

你不需要額外的互斥體 – 0xC0000022L 2012-04-09 16:18:10

回答

2

這個額外的互斥量幾乎肯定是不需要的。 ResetEventSetEvent函數本身可以安全地從多個線程調用

鑑於此代碼確實存在,編寫該代碼的開發人員很可能不明白他們創建的線程語義。我會視任何依賴於該邏輯的代碼爲高度可疑的。從長遠來看,它可能爲您節省一些時間,並預先審覈線程問題的代碼。

+1

已經遍佈全球。 Profiler展示了大量的「快速」鎖的調用。工作系統嚴重濫用。這是我不確定鎖定的最後兩個函數。現在,像你所說的那樣,在代碼中爬行,確保其他所有東西都應該是...... – 2012-04-09 16:25:49

+0

「事件探查器顯示大量的」快速「鎖的調用 - 哦,親愛的:((我很同情。 – 2012-04-09 16:44:20

1

活動是原子的,所以沒有必要使用一個互斥體SetEventResetEvent左右,除非有別的東西與它一起和兩個必須自動完成的(例如,如果你設置一個事件和重置另一)。

+0

不是,沒有那樣的。設置和重置已經在單獨的關鍵部分,但我會檢查以確保它們不應該被鎖定在一起。好的建議。 – 2012-04-09 16:28:59

1

警告程序員!

手動重置事件很難使用,可能需要您鎖定設置和重置事件(自動重置事件可以更輕鬆地避免這些問題)。

考慮以下代碼:

Worker() { 
    WaitForSingleObject(hEvent); 
    DoWork(); 
    ResetEvent(hEvent); 
} 

EventThread() { 
    QueueWork(); 
    SetEvent(hEvent); 
} 

有可能與活潑交織的工人的EventThread已經暗示它之後對事件復位,這將導致工人時,它會等待掛起。要在這種情況下正確使用手動重置事件,您需要獲取重置事件的鎖定,並通過重置事件來自動檢查隊列的狀態。

自動重置事件讓你自動喚醒並重置避免這場比賽的事件(如果你已經在工作進來時已經排隊,但你不會錯過任何醒來) 。