簡體   English   中英

關於自定義事件的問題

[英]Question about custom events

我正在為C#制作自定義事件,有時它不起作用。

這就是我讓事件發生的方式:

    private bool isDoorOpen;
    public bool IsDoorOpen {
        get { return isDoorOpen;}
        private set { isDoorOpen = value; DoorsChangeState(this, null);}
    }

這些是事件聲明:

    //events        
    public delegate void ChangedEventHandler(Elevator sender, EventArgs e);
    public event ChangedEventHandler PositionChanged;
    public event ChangedEventHandler DirectionChanged;
    public event ChangedEventHandler BreaksChangeState;
    public event ChangedEventHandler DoorsChangeState;

只要有事件附加了方法,這就可以工作,但如果沒有,則會拋出空引用異常。 我究竟做錯了什么?

調用事件的推薦方法是

var handler = this.DoorsChangeState;
if (handler != null)
    handler(this, null);

在本地復制處理程序的原因是當您檢查null時,在另一個線程上更改事件處理程序。

編輯:發現文章談論競爭條件。 http://blogs.msdn.com/ericlippert/archive/2009/04/29/events-and-races.aspx

我知道這個問題已經在SO上多次討論(並得到了回答)。

在這里的某處我有以下擴展方法,使這個模式更容易使用:

public static class EventHandlerExtensions
{
    public static void FireEvent<T>(this EventHandler<T> handler, object sender, T args) where T : EventArgs
    {
        var temp = handler;
        if (temp != null)
        {
            temp(sender, args);
        }
    }

    public static void FireEvent(this EventHandler handler, object sender)
    {
        var temp = handler;
        if (temp != null)
        {
            temp(sender, EventArgs.Empty);
        }
    }
}

所以在你的代碼中你可以說:

public bool IsDoorOpen
{
    get { return isDoorOpen;}
    private set
    {
        isDoorOpen = value;
        DoorsChangeState.FireEvent(this);
    }
}

如果事件在觸發時未訂閱,則將拋出NullReferenceException。 這是正確的行為,而不是你做錯了。

你應該檢查:

if(DoorsChangeState != null)
{
   DoorsChangeState(this, null); // Only fire if subscribed to
}

在調用事件之前,您必須檢查事件是否為null:

if (DoorsChangeState != null)   
  DoorsChangeState(this, null);

DoorsChangeState為null時,表示該事件上沒有偵聽器。

您需要檢查事件是否已訂閱。

我使用這個標准形式來拋出我的所有事件。

var temp = EventName;
if(EventName!= null)
   temp(this, null);

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM