如果我有一个可以/将在任何给定时间点被多个线程访问的数组,究竟是什么导致它是非线程安全的,以及将采取什么步骤来确保该数组是线程的在大多数情况下安全吗?
我在 Internet 上广泛查看,几乎没有找到关于这个主题的信息,一切似乎都是特定的场景(例如,这个数组,这两个线程是线程安全的,并且在, 等等)。我真的很希望有人可以回答我在顶部列出的问题,或者有人可以指出一份解释上述项目的好文件。
编辑: 在 MSDN 上四处寻找后,我找到了 ArrayList 类。当您使用 synchronize 方法时,它会为给定的列表返回一个线程安全的包装器。在列表中设置数据时(即 list1[someNumber] = anotherNumber;)包装器会自动处理锁定列表,还是您仍需要锁定它?
最佳答案
当两个线程正在访问完全相同的资源(例如,不是本地副本,而是同一资源的同一副本)时,可能会发生许多事情。在最明显的情况下,如果线程 #1 正在访问资源,而线程 #2 在读取过程中更改它,则可能会发生一些不可预测的行为。即使是像整数这样简单的东西,您也可能会出现逻辑错误,因此请尝试想象不当使用更复杂的东西(例如声明为静态的数据库访问类)可能导致的恐怖。
处理这个问题的经典方法是锁定敏感资源,这样一次只有一个线程可以使用它。所以在上面的例子中,Thread #1 会请求一个资源的锁并被授予它,然后去读取它需要读取的内容。线程 #2 会在读取过程中出现并请求锁定资源,但被拒绝并被告知等待,因为线程 #1 正在使用它。当线程 #1 完成时,它释放锁,线程 #2 就可以继续了。
还有其他情况,但这说明了最基本的问题和解决方案之一。在 C# 中,您可以:
1) 使用由框架管理为可锁定的特定 .NET 对象(如 Scorpion-Prince 的 link to SynchronizedCollection )
2) 使用[MethodImpl(MethodImplOptions.Synchronized)]规定执行危险操作的特定方法一次只能由一个线程使用
3) 使用 lock statement隔离正在执行潜在危险操作的特定代码行
哪种方法最好取决于您的情况。
关于c# - 数组和线程安全访问,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10952146/