C#對觀察者(Observer)模式的支援(二)

來源:互聯網
上載者:User
.Net為我們應用事件定義了標準的模式,我們在應用過程中應遵守定義事件的規則。一個標準的事件模式包括四個方面的內容:

1、 一個繼承自System.EventArgs類型的事件資訊類,並且這個類的名稱以EventArgs結尾,如SendMailEventArgs,這個類負責儲存事件來源發送給事件監聽者的資訊。如果事件來源不需要給事件監聽者傳遞額外的資訊,可以直接使用EventArgs.Empty,這時我們就不用再去定義自己的事件資訊類了。

2、 定義事件時使用的委託(類似於觀察者模式中的抽象主題Subject和抽象觀察者Observer),這個委託傳回型別為void,有兩個參數,第一個參數類型為Object,第二個為System.EventArgs或它的子類,名字應以EventHandler結尾,如:

public delegate void XxxEventHandler(object sender,SendMailEventArgs e);.net架構為我們定義了一個符合事件規範的泛型委派

System.EventHandler<TEventArgs>(Object sender , TeventArgs e) where TeventArgs:EventArgs;

這樣我們在實際應用中就不用再去實現一個自訂委託了,直接用這個泛型委派就可滿足我們應用事件的需要。

3、 一個負責通知事件訂閱者的事件來源類(類似於觀察者模式中的具體主題ConcreteSubject),這個類包含一個事件成員,負責向外提供事件的訂閱和登出介面,並儲存他們的狀態;一個負責引發事件的方法以通知所有這個事件的訂閱者,這個方法需要是一個受保護的虛方法,並且是以On開頭以事件名字結尾,並且接受一個類型為System.Eventargs(或子類)的參數。如定義一個事件成員:

public event EventHandler<SendMailEventArgs> SendMail;

那麼這個方法應為:

PRotected virtual void OnSendMail(SendMailEventArgs e){};

還有一個負責將外部調用或輸入轉化為期望事件的方法,估且叫做觸發器吧。

這個方法負責執行個體化一個事件訊息類,調用引發事件的方法OnXxx,並將事件訊息執行個體傳遞過去。

4、 事件監聽者類(類似於觀察者模式中的具體觀察者ConcreteObserver),用來監聽事件來源發出的訊息,這個類用來定義和事件相相容的方法,格式為傳回值為void,有兩個參數,第一個參數類型為Object,第二個為相應的事件訊息類。例:protected void Phone_SendMail(Object sender,EventArgs e)……;

下面改寫上篇文章中的郵件發送系統:

首先定義一個事件訊息類,這個類負責儲存向裝置發送的訊息。

view plaincopy to clipboardprint?
public class SendMailEventArgs:EventArgs
{
//唯讀資訊欄位
public readonly string Message;
public SendMailEventArgs(string message)
{
this.Message = message;
}
}
public class SendMailEventArgs:EventArgs
{
//唯讀資訊欄位
public readonly string Message;
public SendMailEventArgs(string message)
{
this.Message = message;
}
}

事件來源類.

view plaincopy to clipboardprint?
class MailManager
{
//郵件
public System.Net.Mail.MailMessage MailMess
{
set
{
MailMess = value;
}
get
{
return new System.Net.Mail.MailMessage();
}
}
//用.net架構提供的泛型委派定義一個事件
public event EventHandler<SendMailEventArgs> SendMail;
//負責引發事件的方法
protected virtual void OnSendMial(SendMailEventArgs e)
{
EventHandler<SendMailEventArgs> sendMail=SendMail;
if (sendMail != null)
{
//通知所有訂閱者
sendMail(this, e);
}
}
//負責將外部調用轉化為事件
public void SendToMail()
{
if (String.IsNullOrEmpty(MailMess.Subject) || string.IsNullOrEmpty(MailMess.Body))
{
Console.WriteLine("郵件發送失敗!");
}
else
{
Console.WriteLine("發送郵件:{0}", MailMess.Subject);
//用郵件的Subject執行個體化一個事件資訊類
SendMailEventArgs sendMailEventArgs = new SendMailEventArgs(MailMess.Subject);
//通知所有事件訂閱者
this.OnSendMial(sendMailEventArgs);
}
}
}
class MailManager
{
//郵件
public System.Net.Mail.MailMessage MailMess
{
set
{
MailMess = value;
}
get
{
return new System.Net.Mail.MailMessage();
}
}
//用.net架構提供的泛型委派定義一個事件
public event EventHandler<SendMailEventArgs> SendMail;
//負責引發事件的方法
protected virtual void OnSendMial(SendMailEventArgs e)
{
EventHandler<SendMailEventArgs> sendMail=SendMail;
if (sendMail != null)
{
//通知所有訂閱者
sendMail(this, e);
}
}
//負責將外部調用轉化為事件
public void SendToMail()
{
if (String.IsNullOrEmpty(MailMess.Subject) || string.IsNullOrEmpty(MailMess.Body))
{
Console.WriteLine("郵件發送失敗!");
}
else
{
Console.WriteLine("發送郵件:{0}", MailMess.Subject);
//用郵件的Subject執行個體化一個事件資訊類
SendMailEventArgs sendMailEventArgs = new SendMailEventArgs(MailMess.Subject);
//通知所有事件訂閱者
this.OnSendMial(sendMailEventArgs);
}
}
}

事件監聽類

view plaincopy to clipboardprint?
class MobilePhone
{
#region SendHandler 成員

public void SendMessage(object sender,SendMailEventArgs e)
{
Console.WriteLine("手機資訊:{0}", e.Message);
}

#endregion
}
public class RTX
{
#region SendHandler 成員

public void SendMessage(object sender,SendMailEventArgs e)
{
Console.WriteLine("RTX資訊:{0}", e.Message);
}

#endregion
}
class MobilePhone
{
#region SendHandler 成員

public void SendMessage(object sender,SendMailEventArgs e)
{
Console.WriteLine("手機資訊:{0}", e.Message);
}

#endregion
}
public class RTX
{
#region SendHandler 成員

public void SendMessage(object sender,SendMailEventArgs e)
{
Console.WriteLine("RTX資訊:{0}", e.Message);
}

#endregion
}



下面是用戶端的調用

view plaincopy to clipboardprint?
class Program
{
static void Main(string[] args)
{
//事件監聽源執行個體
MailManager mailManager = new MailManager();
//為Mail添加主題和內容
mailManager.MailMess.Subject = "通知";
mailManager.MailMess.Body = "觀察者模式的學習。";
mailManager.SendMail+=new MobilePhone().SendMessage;//註冊手機通知
mailManager.SendMail+=new RTX().SendMessage;//註冊RTX通知
mailManager.SendToMail();//發送郵件
Console.WriteLine("按任意鍵繼續……");
Console.ReadKey();
}
}

以上就是C#對觀察者(Observer)模式的支援(二)的內容,更多相關內容請關注topic.alibabacloud.com(www.php.cn)!

  • 相關文章

    聯繫我們

    該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

    如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

    A Free Trial That Lets You Build Big!

    Start building with 50+ products and up to 12 months usage for Elastic Compute Service

    • Sales Support

      1 on 1 presale consultation

    • After-Sales Support

      24/7 Technical Support 6 Free Tickets per Quarter Faster Response

    • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.