【问题标题】:why introduce a temp variable? [duplicate]为什么要引入临时变量? [复制]
【发布时间】:2014-08-16 22:05:31
【问题描述】:

我看到了很多以下事件处理程序的用法。为什么他们将处理程序分配给局部变量然后使用局部变量?

event EventHandler PropertyChanged;

private void RaisePropertyChanged(string propertyName)
{
    var temp = PropertyChanged;
    if (temp != null)
        temp(this, new PropertyChangedEventArgs(propertyName));
    // why not just "if (PropertyChanged != null) PropertyChanged(...)" 
}

【问题讨论】:

    标签: c# events


    【解决方案1】:

    临时变量确保线程安全,因为在检查和实际调用之间,其他线程可能会取消订阅该事件,这将导致NullReferenceException

    Eric Lippert 有a great article on this

    【讨论】:

    • 如果我正在编写一个只在表单加载事件中分配事件处理程序的 winforms 应用程序,我可以忽略该模式吗?后台工作人员用于分配控件的数据源。
    • +1 感谢文章的链接
    • @dc7a9163d9 提到后台工作者意味着你已经做了一些多线程,所以我建议坚持使用 temp 变量。
    • 无论如何我都会使用这个模式。只是好奇如果后台工作人员从不取消订阅事件处理程序是否安全。
    【解决方案2】:

    因为 PropertyChanged 可能由于其他线程的操作而改变;特别是,它可以在 null 检查和调用之间设置为 null。

    【讨论】:

      【解决方案3】:

      因为在多线程环境中,如果事件的最后一个订阅者在 if 之后但在调用之前取消订阅,您将获得 NullRefrenceExecption。通过首先在本地复制委托,它不能再被取消订阅修改。

      【讨论】:

        【解决方案4】:

        想象一下:

        if (PropertyChanged)
          PropertyChanged(...)
        

        现在就在if 之后,操作系统跳过线程,新的线程将删除唯一的订阅。在这之后PropertyChangednull,你就有麻烦了。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2012-11-29
          • 1970-01-01
          • 1970-01-01
          • 2015-07-28
          • 2016-12-04
          相关资源
          最近更新 更多