避免或减轻 C# 中共享相同变量(资源)的两个函数的竞争条件

问题描述 投票:0回答:1
  • 我在不同的类中有两个函数,它们正在生成竞争条件。

  • 一个函数正在更新变量值,另一个函数正在使用变量,我假设它们处于竞争状态。

  • counter
    变量可以从两个函数访问。
    var counter=0
    ;

  • 两个函数在不同的类中。

函数更新值

protected void updateValue(SomeClassType val){
  // Based upon some condition value for variable is updated
  if(val.id){ // some condition
    counter=2;
  }
}

函数使用值

protected void useValue(var counter){
  // Do something with variable.
}
  • upateValue
    功能在
    worker-thread
    中运行。
    useValue
    正在运行
    main-thread
    .
  • 我需要的是
    useValue
    应该等到
    updateValue
    ,更新变量值。

我试过的

  • 创建了
    AutoResetEvent
    .
  • 的一个静态对象
public static AutoResetEvent autoResetEventForUpdateValue = new AutoResetEvent(false);
protected void updateValue(SomeClassType val){
  // Based upon some condition value for variable is updated
  if(val.id){ // some condition
    counter=2;
  }
  autoResetEventForUpdateValue.Set();
}

函数使用值

WaitHandle[] waitHandles = new WaitHandle[] { autoResetEventForUpdateValue};
protected void useValue(var counter){
  // Do something with variable.
}

还有

updateValue(val)
,这个
val
类型的参数
SomeClassType
在类
useValue(counter)
的实现中不可访问。

  • 在调试时使用我的解决方案,我意识到
    useValue
    继续等待并且
    updateValue
    没有初始化为
    worker-thread
    没有在那里运行。
c# multithreading race-condition autoresetevent waithandle
1个回答
1
投票

我只想更改

UpdateValue
以返回值而不是就地更新它,这应该使订购变得微不足道:

var currentCounterValue = ...
var updatedCounterValue = await Task.Run(() => ComputeNewCounterValue(currentCounterValue));
UseValue(updatedCounterValue );

纯方法,即没有副作用的方法,其结果仅取决于输入,往往是最容易使用的。在处理多线程时尤其如此。

您可能还需要某种机制来确保您的方法不能同时运行。如果这是由按下按钮触发的,您可以在调用

ComputeNewCounterValue
之前禁用该按钮,并在
UseValue
;

之后启用它
© www.soinside.com 2019 - 2024. All rights reserved.