2012-11-29 20 views
6

我們可以從兩個方面提高事件:.NET事件認識和NullObject模式

public event EventHandler MyEvent; 

private void DoSomething() 
{ 
    ... 
    var handler = MyEvent; 
    if (handler != null) 
     handler(this,EventArgs.Empty); 
} 

public event EventHandler MyEvent = (o,e) => {} ; 

private void DoSomething() 
{ 
    ... 
    MyEvent(this, EventArgs.Empty); 
} 

我喜歡最後一個。它更短。
我的同事堅持第一個變體。

第一個和第二個有什麼優勢嗎?

+0

您至少可以簡化第一個'如果(this.MyEvent!= NULL)this.MyEvent(這一點,EventArgs.Empty);' –

+5

@JonB:錯了;這不是線程安全的。 – SLaks

+3

你將如何防止課程將事件設置爲空? –

回答

11

更新爲C#6

在C#6你只需使用空條件運算符,像這樣:

PropertyChanged?.Invoke(this, args); 

這是​​

原來的答案

Eric Lippert擁有a great blog post on Events and Races,你應該閱讀,如果你沒有。

第一個選項可以被認爲比第二個選項更安全,因爲事件可以設置爲null。有人可能會不小心修改課程。另外,如果反序列化實例,第二種方法將不起作用(取決於您使用的序列化機制)。

我有時用一個輔助的方法來引發事件

static class Raiser 
{ 
    public static void Raise<T>(this EventHandler<T> evnt, object sender, T args) 
     where T : EventArgs 
    { 
     if (evnt != null) 
     { 
      evnt(sender, args); 
     } 
    } 
} 

class SomeClass 
{ 
    public event EventHandler<EventArgs> MyEvent; 

    private void DoSomething() 
    { 
     MyEvent.Raise(this, EventArgs.Empty); 
    } 
} 
+0

最好的兩個世界和很好的擴展方法的使用,得到我的橙色箭頭。 – Paolo

+0

好幫手法。謝謝! –

+0

我同意你的觀點,但我對'粗心的修改'感興趣。這是否意味着我應該檢查一個方法中的任何變量,這個方法可能會在代碼中的其他地方被意外更改?我認爲這是代碼合同不變的原因。 –