【问题标题】:C# - Lock method on value of variable (Threading)C# - 变量值的锁定方法(线程)
【发布时间】:2017-02-13 12:19:30
【问题描述】:

我在线程方面没有太多经验,但在这个项目中,我需要一些线程来通过 Com 端口从 SPS 请求数据。 我有不同的线程在运行,可能会发生 2 个甚至更多的线程想要访问同一个 Com-Port,这当然是行不通的。
现在我的问题是我是否可以将调用的方法锁定在变量的值上,该变量将是 Com-Port 的编号,而具有不同值的线程可以进入方法。
顺便说一句:我不能使用不同的变量作为锁的“键”,因为我从数据库中动态获取值。
我的代码可能如下所示:

Main()
{
   Start different Threads calling myMethod
}

myMethod()
{
   lock on value of a Variable
   {
      some code...
   }
}

【问题讨论】:

  • 您需要使用引用类型作为锁定对象,因此 Com-Port 的编号 不起作用。这取决于一些代码...你必须锁定什么
  • 这里有什么问题?

标签: c# multithreading thread-safety locking


【解决方案1】:

我认为您最好的解决方案是创建一个包含 myMethod 的类并为每个端口实例化它。

如果你不想这样做,你可以(例如)定义一个线程安全的锁字典

public static ConcurrentDictionary<int, object> locks = new ConcurrentDictionary<int, object>(); 

在开始线程之前对其进行初始化:

for (int i=0; i < 10; i++)
{
    locks[i] = new object();
}

并按端口号锁定:

lock(locks[portnum])
{
    some code...
}

当然假设您知道 myMethod 上下文中的端口号(否则您将如何访问特定端口?)。

【讨论】:

  • 如果some code... 使用没有为每个端口初始化的共享资源,这也不是线程安全的。此外,如果以后可以修改此字典,您应该使用 ConcurrentDictionary
  • 你是对的! ConcurrentDictionary 是要使用的正确对象 - 我编辑了我的答案。关于您的另一点,您当然是正确的,但是 OP 没有指定他使用哪些对象,因此不可能给出涵盖所有共享资源的具体示例。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多