【问题标题】:Resource Access by Parallel Threads并行线程的资源访问
【发布时间】:2013-11-19 06:24:23
【问题描述】:

我有 2 个线程要同时触发并并行运行。这两个线程将处理一个字符串值,但我想确保没有数据不一致。为此,我想使用带有Monitor.PulseMonitor.Wait 的锁。我使用了在另一个问题/答案中找到的方法,但是每当我运行程序时,第一个线程都会卡在Monitor.Wait 级别。我认为那是因为第二个线程已经“脉冲”和“等待”。下面是一些代码:

string currentInstruction;

public void nextInstruction() 
{
    Action actions = {
        fetch,
        decode
    }
    Parallel.Invoke(actions);
    _pc++;
}

public void fetch()
{
    lock(irLock) 
    {
        currentInstruction = "blah";
        GiveTurnTo(2);
        WaitTurn(1);
    }

    decodeEvent.WaitOne();
}

public void decode()
{
    decodeEvent.Set();

    lock(irLock) 
    {
        WaitTurn(2);
        currentInstruction = "decoding..."
        GiveTurnTo(1);
    }
}

// Below are the methods I talked about before.

// Wait for turn to use lock object
public static void WaitTurn(int threadNum, object _lock)
{
    // While( not this threads turn )
    while (threadInControl != threadNum)
    {
        // "Let go" of lock on SyncRoot and wait utill 
        // someone finishes their turn with it
        Monitor.Wait(_lock);
    }
}

// Pass turn over to other thread
public static void GiveTurnTo(int nextThreadNum, object _lock)
{
    threadInControl = nextThreadNum;
    // Notify waiting threads that it's someone else's turn
    Monitor.Pulse(_lock);
}

知道如何让 2 个并行线程在同一个周期内使用锁或其他任何东西进行通信(操作相同的资源)吗?

【问题讨论】:

  • 您并行调用 fetch 和 decode,但同时锁定它们,因此在任何给定时间只有一个可以执行。您应该考虑一下您的程序,一定有更好的方法。

标签: c# multithreading locking


【解决方案1】:

您想并行运行 2 段代码,但在开始时使用相同的变量锁定它们?

正如 nvoigt 提到的,这听起来已经不对了。您需要做的是从那里删除lock。仅当您要以独占方式访问某些内容时才使用它。

顺便说一句,“数据不一致”可以通过不必拥有它们来避免。不要直接使用currentInstruction 字段(它是一个字段吗?),而是提供一个线程安全的CurrentInstruction 属性。

private object _currentInstructionLock = new object();
private string _currentInstruction
public string CurrentInstruction
{
    get { return _currentInstruction; }
    set
    {
        lock(_currentInstructionLock)
            _currentInstruction = value;
    }
}

还有一点是命名,以_ 开头的局部变量名是一种不好的风格。有些人(包括我)使用它们来区分私有领域。属性名称应以 BigLetter 开头,局部变量应从Small 开头。

【讨论】:

  • 谢谢。根据我对锁的理解,我很快就把它放在一起,但是当它不起作用时就丢失了。我在每种方法中都使用了等待句柄。你认为我可以操纵这些来使我想要实现的目标受益吗?我将编辑我的问题以反映我的意思。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-05-31
  • 2018-06-01
  • 2020-05-30
  • 2020-11-01
  • 1970-01-01
相关资源
最近更新 更多