一尘不染

在事件处理程序中使用空值检查

c#

在检查事件处理程序是否为null时,这是否基于每个线程进行?

确保有人正在听事件是这样完成的:

EventSeven += new DivBySevenHandler(dbsl.ShowOnScreen);

如果我按照此模式在上面检查空值的位置添加代码,那么为什么我需要进行空值检查(从此站点获取的代码)。我想念什么?

此外,事件和GC的规则是什么?


阅读 182

收藏
2020-05-19

共1个答案

一尘不染

恐怕您的意思确实不清楚,但是如果委托有可能为null,则需要在每个线程上分别进行检查。通常,您会这样做:

public void OnSeven()
{
    DivBySevenHandler handler = EventSeven;
    if (handler != null)
    {
        handler(...);
    }
}

这样可确保即使您EventSeven在执行过程中进行更改OnSeven()也不会得到任何帮助NullReferenceException

但您说对了,如果您确实有订阅处理程序,就不需要null检查。这可以在C#2中使用“无操作”处理程序轻松完成:

public event DivBySevenHandler EventSeven = delegate {};

另一方面,如果您可能从各种线程获得预订,则 可能
需要某种锁定只是为了确保您拥有“最新”的处理程序集。我的线程教程中有一个示例可以提供帮助-
尽管通常我建议您尽量避免使用它。

在垃圾回收方面,事件 发布者 最终会引用事件 订阅者 (即处理程序的目标)。仅当发布者的寿命要长于订阅者时,这才是问题。

2020-05-19