在两个不同的代码块使用相同的锁对象?

时间:2012-02-22 23:58:31

标签: c# multithreading locking

我可以在两个方法中使用相同的锁定对象,由两个不同的线程访问吗?目标是使task1和task2线程安全。

object lockObject = new object();

// Thread 1
void Method1()
{
    lock(lockObject)
    {
        // task1
    }
}

// Thread 2
void Method2()
{
    lock(lockObject)
    {
        // task2
    }
}

3 个答案:

答案 0 :(得分:21)

是的,您可以使用相同的锁定对象(从技术上讲,它是计算机科学意义上的monitor,并通过两种不同方法调用System.Monitor中的方法实现)。

所以,假设你有一些静态资源r,并且你想要两个线程来访问该资源,但是一次只能有一个线程使用它(这是锁的经典目标)。然后你会编写像

这样的代码
public class Foo
{
    private static object _LOCK = new object();

    public void Method1()
    {
        lock (_LOCK)
        {
            // Use resource r
        }
    }

    public void Method2()
    {
        lock (_LOCK)
        {
            // Use resource r
        }
    }
}

您需要锁定程序中r的每次使用,否则两个线程可以同时使用r。此外,您必须使用相同的锁,否则两个线程将同时使用r。因此,如果您在两种不同的方法中使用r,则必须使用两种方法中的相同锁定。

编辑:正如@diev在评论中指出的那样,如果资源是Foo类型对象上的每个实例,我们就不会使_LOCK成为静态,而是会_LOCK实例级数据。

答案 1 :(得分:5)

如果你想阻止不同的线程同时执行task1和task2,那么你必须使用相同的锁对象。

如果两个任务不争用相同的资源,则可以使用不同的锁定对象。

答案 2 :(得分:4)

你可以而且有效。如果您不使用同一个对象,则可以同时执行这些块。如果你确实使用同一个对象,他们就可以了。

另外,您的意思是lock(lockObject),而不是using(lockObject)