2010-02-23 44 views
7

穿線文字說明在閱讀C#果殼 3.0通過約瑟夫和Ben阿爾巴哈利,我碰到下面的段落(673頁來了,部分第一段標題「信令與等待和脈衝」)在「C#3.0果殼中的」

「的監視器類提供另一個信令經由兩個靜態方法構造,等待脈衝。其原理是,你使用自定義的標誌和字段(包含在語句)自己寫的信令邏輯,然後介紹等待脈衝命令,以減輕CPU紡紗。這種低層次的方法的優點是隻等待脈衝聲明,就可以實現功能的AutoResetEvent的ManualResetEvent,並信號燈,以及WaitHandle的靜態方法WaitAllWaitAny。此外,等待脈衝 可以在以下情況下適合在那裏 所有的等待句柄都 吝嗇的挑戰。」

我的問題是,什麼是最後句子的正確解釋是什麼?

  • 一個體面/大量等待的情況處理,其中的WaitOne()只是偶爾叫上任何特定的等待句柄。
  • 有一個體面的/大量的等待句柄的情況,很少有多個線程傾向於阻塞任何特定的等待句柄。
  • 一些其他解釋。

也希望照亮這些情況的例子,以及可能如何和/或爲什麼他們更有效地通過等待和脈衝而不是其他方法處理。

謝謝!

編輯:我發現文本在線here

+1

你需要引入更多的上下文,因爲並不是所有讀你的問題的人都讀過這本書。 – Vlad 2010-02-23 23:59:23

+0

也許Joe Albahari可能正在看... – 2010-02-24 00:11:16

+0

@Vlad完成了! @Mitch嗯,我可以希望:) – RAL 2010-02-24 00:16:32

回答

5

這是什麼意思是,有一些情況下等待和脈衝提供了比等待句柄簡單的解決方案。在一般情況下,這種情況出現:

  • 服務員,而不是發出通知,決定何時解除
  • 阻塞條件涉及比一個簡單的標誌更多(可能是幾個變量)

你可以在這些情況下仍然使用等待句柄,但等待/脈衝往往更簡單。 Wait/Pulse最棒的地方在於Wait在等待時釋放底層鎖。 - 例如,在下面的例子中,我們讀鎖的安全範圍內_x和_y,但該鎖在等待,以便其他線程可以更新這些變量發佈:

lock (_locker) 
{ 
    while (_x < 10 && _y < 20) Monitor.Wait (_locker); 
} 

另一個線程就可以更新_x和原子_y(由於鎖定),然後脈衝信號服務員:

lock (_locker) 
{ 
    _x = 20; 
    _y = 30; 
    Monitor.Pulse (_locker); 
} 

等待/脈衝的缺點是,它更容易得到它錯了,犯了一個錯誤(例如,通過更新變量並忘記脈衝)。在有等待句柄的程序對於有Wait/Pulse的程序同樣簡單的情況下,我建議使用等待句柄出於這個原因。在效率/資源消耗方面(我認爲您所指的是),等待/脈衝通常更快更輕(因爲它具有託管實現)。不過,這在實踐中並不是什麼大問題。在這一點上,Framework 4.0包含低開銷的管理版本的ManualResetEvent和Semaphore(ManualResetEventSlim和SemaphoreSlim)。

Framework 4.0中還規定,爲減少等待/脈衝,需要更多的同步選項:

  • CountdownEvent
  • 屏障
  • PLINQ /數據並行(進行AsParallel,Parallel.Invoke,的Parallel.For, Parallel.ForEach)
  • 任務和延續

所有這些都是高得多-LEV比Wait/Pulse和IMO更適合編寫可靠和可維護的代碼(假設他們將解決手頭的任務)。

+0

只是一個猜測......但你似乎有內部的軌道上作者可能意思是:) 非常感謝! – RAL 2010-02-24 01:39:00

+1

對不起 - 我應該說我是文章的作者:) – 2010-02-24 01:48:03