【问题标题】:Multithreading scenario for list列表的多线程场景
【发布时间】:2013-01-15 16:51:42
【问题描述】:

我已阅读此模式,但发现它不起作用。我遇到了一个罕见的异常,即 foreach 中的项目已更改。

锁定(我的列表) { foreach(var a in myList) {}

myList = new List() (或 myList.Clear() ) }

我也试过了

foreach(var a in myList.ToList()) { }

这也产生了异常。此线程中描述了一些其他模式,但我想确认/理解为什么上述模式不起作用 我已经阅读了一些关于如何正确锁定列表的内容。该异常并不经常发生——只是非常罕见,而且当时还存在内存泄漏。

1。 我是否需要在修改 myList 的任何地方都使用该锁,或者该锁是否会阻止任何人编辑 mylist?这可能是混乱的根源。

2.

lock mylist 和强制转换和使用 syncroot 有区别吗?

看这里

Properly locking a List<T> in MultiThreaded Scenarios?

【问题讨论】:

  • 关于 1:是的,您需要锁定修改列表甚至读取列表的任何位置。这就是应该使用锁的方式。
  • 这里有一本很棒的(免费的)电子书:Albahari

标签: winforms multithreading list


【解决方案1】:

通常,如果您有共享资源,那么您需要锁定一个互斥锁,以在您使用该资源时保护该资源。不管是读还是写都无所谓。如果互斥锁未锁定在您使用共享资源的至少一个地方,那么您就有问题了。例如,如果您只在修改共享资源时锁定它,那么可能某个线程正在读取它,而另一个线程正在修改它——这种情况称为竞争条件。

在您的特定情况下,是的,您需要在修改 mylist 的任何地方锁定它。不仅在你修改它的地方,而且在你阅读它的任何地方。

【讨论】: