在同一个方法中有 2 个锁的坏习惯?

Bad practice having 2 locks in same method?

我想知道在同一个方法中使用 2 个单独的锁是否是一个糟糕的代码设计。我相信首先实现这两个锁的原因是它们更新的字段不相关。

public class MyClass
{
  private readonly object _lock = new object();
  private readonly object _lock2 = new object();

  public async Task DoStuff()
  {
    lock(_lock)
    {
      //do some stuff
    }
    lock(_lock2)
    {
      //do some other stuff
    }
  }
}

假设 _lock 仅用于修改 int 变量,而 _lock2 用于修改 List<string> 变量。可以从 class 中不同线程上的其他方法调用这两个锁。这里有死锁的味道吗?看来我应该重构它,所以 DoStuff 方法应该只使用一种锁类型。

如果两个代码块 运行 同时来自不同的调用是可以的,那么 lock 有两个对象就没有问题。如果 重要 这两个块能够同时 运行 那么你 有不同的对象是很重要的 lock上。如果两个块实际上不是同时 运行 很重要,并且整个操作被视为一个逻辑上的原子操作,那么您应该使用一个 lock.

这两个选项具有完全不同的语义,既不是天生错误也不是天生正确。你需要根据你所处的情况使用正确的。

该代码是死锁安全的。这段代码中没有锁会阻止已经在临界区的线程离开它的情况。因此这个线程总是会为另一个线程释放获得的锁