您看到的錯誤告訴您,您正在嘗試在枚舉它時修改集合。 lock
關鍵字適用於多線程情況,它確保只有一個線程處於關鍵部分。它與「鎖定」收集無關,因此您可以枚舉它並修改它。
您通常看到的錯誤與代碼中出現一樣,如果你有一個線程枚舉集,而其他線程添加或刪除收集以下
foreach(var item in items)
{
//Inside this loop now you are enumerating collection
//This means you can't add or delete anything from items
items.Add(newItem); //This will produce the error you are seeing
}
也可能會出現此錯誤。所以如果你知道你有多線程的情況,那麼你可以使用lock
,雖然它有點棘手,可能會影響你的併發性能,甚至會導致競爭狀態。對於多線程情況,僅使用ToList
可能不夠,因爲在調用ToList
時需要確保只有一個線程可以訪問集合。因此,您可能需要使用ToList
以及鎖定,根據您的情況,它可能會更簡單。要查看如何在枚舉中進行線程安全修改的示例,請參閱此答案:Making a "modify-while-enumerating" collection thread-safe。
如果你知道你沒有多個線程,那麼ToList
可能是你唯一的選擇,你根本不需要lock
。我還建議確定在枚舉時是否確實需要修改集合。在許多情況下(但不是全部),您可以採取不同的設計,以避免它首先出現。
鎖不起作用的情況下,列表在同一個線程上更改並且ToList不能使用列表線程安全 – Steven
這是在WCF服務中,我最好檢查線程。我總是對線程和WCF感到困惑。 –
一般而言,Web服務可能意味着您的代碼在理論上*在一個仲裁線程上被訪問*。在我的Web服務中,我使用'ReadWriterLockSlim'來確保集合讀取處於讀取鎖定狀態,並且在更新時顯然是寫入鎖定。 –