【问题标题】:Does a method marshalled on the UI Thread need to be thread-safe在 UI 线程上编组的方法是否需要是线程安全的
【发布时间】:2011-06-24 13:41:45
【问题描述】:

如果我在 UI 线程上调用一个方法,它是否会被 Windows 消息队列海化并且随后不需要重新进入?

    private void CalledFromWorkerThread()
    {
        //changed from 'InvokeRequired' Anti-Pattern
        this.Invoke((Action) (() => _counter++; /* Is this ok? */ ));
    }

澄清:只有 UI 线程会访问 _counter。

【问题讨论】:

  • 如果你还没有在柜台上锁,你也应该使用。
  • 测试InvokeRequired 是一种反模式。 Control.Invoke 已经包含这样的检查。
  • @0A0D Skeet 先生没有在上述链接中调用的方法中使用锁?如果只是访问_counter 的 UI 线程是安全的,那是我最初的问题吗?
  • 是的,只要是UI线程,你就对了。

标签: c# winforms multithreading


【解决方案1】:

假设 _counter 仅由 UI 线程访问,您所拥有的一切都很好。

如果有两个线程调用您的CalledFromWorkerThread,那么 _counter 将正确递增,并且与您所拥有的线程安全。

【讨论】:

    【解决方案2】:

    根据澄清,只有 UI 线程正在访问 _counter,您不需要锁。我已经更新了我的示例。我更喜欢以这种方式编码以避免额外的 if 调用所需的检查。

    private void CalledFromWorkerThred()
    {
        this.Invoke((Action) (() => _counter++; ));
    }
    

    【讨论】:

      【解决方案3】:

      它将委托来自同一个线程的调用,并不一定意味着您在该函数中执行的所有其他操作都是线程安全的。

      【讨论】:

      • 假设这是更改该字段的唯一代码!它是线程安全的吗?
      • 那么它是唯一访问它的线程(因此它不需要是线程安全的)。所以,是的,它是安全的。
      猜你喜欢
      • 2016-05-08
      • 2010-11-06
      • 2013-12-07
      • 2016-11-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多