2012-02-19 62 views
0
class Class1 
    { 
     private static object consoleGate = new Object(); 

     private static void Trace(string msg) 
     { 
      lock (consoleGate) 
      { 
       Console.WriteLine("[{0,3}/{1}]-{2}:{3}", Thread.CurrentThread.ManagedThreadId, 
        Thread.CurrentThread.IsThreadPoolThread ? "pool" : "fore", 
        DateTime.Now.ToString("HH:mm:ss.ffff"), msg); 
      } 
     } 
     private static void ProcessWorkItems() 
     { 
        lock (consoleGate) 
        { 
         for (int i = 0; i < 5; i++) 
         { 
          Trace("Processing " + i); 
          Thread.Sleep(250); 
         } 
        } 
      Console.WriteLine("Terminado."); 

     } 
     static void Main() 
     { 
      ProcessWorkItems(); Console.ReadLine(); 
     } 
    } 

輸出:同步線程:這裏有衝突嗎?

Processing 0 
Processing 1 
Processing 2 
Processing 3 
Processing 4 
Terminated 

這是爲什麼代碼工作? ProcessWorkItems靜態方法鎖定ConsoleGate對象和Trace做的一樣。我以爲這個物體只能被鎖定一次。 ¿一些解釋?

回答

4

C#中的鎖是可重入的 - 單個線程可以多次獲取相同的鎖而不會阻塞。正弦你只有一個線程在這裏沒有問題 - 鎖是用來同步跨多個線程資源的訪問。

MSDN documentationlock

鎖定關鍵字可確保在另一個線程是在臨界段一個線程不進入代碼的臨界 部。如果 另一個線程試圖輸入一個鎖定代碼,它將等待,阻止, ,直到對象被釋放。

有關重入鎖的更多信息請參閱本SO螺紋:"What is the Re-entrant lock and concept in general?"

1

所有你已經在這裏顯示的代碼是相同的線程上運行。這就是爲什麼它運行就像它會如果你沒有使用「鎖定」