《.Net框架程序设计》读书笔记 之 事件与委托

基础:
    1. .net框架约定,所有保存事件信息的类型都应该继承自System.EventArgs,并且类型名称应该以EventArgs结尾;委托类型应该以EventHandler结束,回调方法原型应该有一个void返回值,并且接受两个参数, 第一个Object指向发送通知的对象;第二个参数继随自EventArgs类型,包括接受者需要的附加信息。
     2.如果定义的事件没有传递 给事件接收者的附加信息,便不必定义新的委托,直接使用System.EventHandler,并将EventArgs.Empty传递给第2个参数即可
public delegate void EventHandler(Object sender, EventArgs e);

.net框架程序设计
最简间的事件与委托关联
//定义委托
public delegate void RequestHandler(string Url);
//定义委托类型的事件
public event RequestHandler RequestEvent;
//定义事件处理程序,即委托的回调方法
public void RequestMothed(string url)
{
    
//do what you want to do;
}

//将事件处理程序添加到委托链
RequestHandler handler = new RequestHandler(RequestMothed);
//将委托对象添加到事件链中,删除委托对象用 -=
RequestEvent += handler;
//引发事件,可将事件当一个方法看待,参数必须与前面声明的一致
RequestEvent(stringTest);

事件可用的修饰符:

Static   Virtual    Override    Abstract

Static类似于字段,类的甩的对象共享静态事件,当引用这类事件时,必须用类名称而不是名称


一:登记事件
定义一个收邮件的类MailManager,在MailManager中定义一个收到邮件便触发的事件MailMSG,传真fax寻呼pager等对象在登记MailManager和MailMSG事件,当新电子邮件到达时,MailManager将通知发送给所有登记对象,这些对象按自己的方法处理。  开始代码.

class MailManager
{
   
//在MailManager类中定义MailMsgEventArgs类型
   public class MailMsgEventAgrs:EventArgs
   
{
        
public MailMsgEventArgs(string from, string to, string subject, string body)
        
{
            
this.from=from;
            
this.to=to;
            
this.subject=subject;
            
this.body=body;
        }

        
public readonly string from, to, subject, body;
   }


   
//定义委托
    public delegate void MailMsgEventHandler(Object sender, MailMsgEventArgs args);

   
//定义委托类型 的事件
   public event MailMsgEventHandler MailMsg;

   
//此方法发出通知,即有邮件是通知FAX和PAGER  ,Fax和PAGER类可以重写些方法
   public virtual void OnMailMsg(MailMsgEventArgs e)
   
{
      
//判断是否有对象登记事件
      if(MailMsg != null)
      
{
          
//如果有,则通知委托链表上的所有对象
          MailMsg(this, e);
      }

     
   }

   
   
//此方法在新电子邮件到达到被触发
   public void SimulateArrivingMsg(string from, string to, string subject, string body)
   
{
            MailMsgEventArgs e 
= new MailMsgEventArgs(from, to, subject, body);
            OnMailMsg(e);
   }

}
其中   编辑器编译public event MailMsgEventHandler MailMsg;时,会产生
二:侦听事件
class Fax
{
   
//将MailManager对象传递给构造器
    public Fax(MailManager mm)
    
//将回调函数与事件关联
    mm.MailMsg += new MailManager.MailMsgEventHandler(FaxMsg);
    
//回调函数
          {
        
//sender 表示MailManagercf 对象,如果要和事件触发者通信,将用到此参数
         
//MailManager 对象希望提供的一些附加事件信息
         
//Fax内部的处理
         Console.WriteLine("Form:{0}\n To:{1}\n Subject: {2}\n: {3}\n", e.from, e.to, e,subject, e.body);
    }

    

    public void Unregister(MailManager mm)
   
{
         //构造一个指向FaxMsg回调方法垢MailMsgEventHandler委托实例
      MailManager.MailMsgEventHandler callback 
= new MailManager.MalMsgEventHandler(FaxMsg);
      
//注销MailManager的MailMsg事件
       mm.MailMsg -= callback;
   }

}

其中,编辑器处理mm.MailMsg += new MailManager.MailMsgEventHandler(FaxMsg);
时会将它转换为
mm.add_MailMsg(new MailManager.MailMsgEventHandler(FaxMsg));
//调用了前面public event MailMsgEventHandler MailMsg编辑的产生的代码  public virtual void add_MailMsg()方法,所以此方法里面有一个是MailMsgEventHandler委托的实例。

三:显式控制事件注册,实际上就将public event MailMsgEventHandler MailMsg编辑时产生的内部代码源码化
Class MailManager
{
   
//传给事件接受者的类型信息,类似于前的
   public class MailMsgEventAgrs : EventArgs{..}
   
//定义委托
   public delegate void MailMsgEventHandler(Object sender, MailMsgEventArgs args);

  
//变化发生在这里,和前面编辑器内部产生代码一样
   private MailMsgEventHandler mailMesgEventHandlerDelegate;
  
//显式定义事件及其访问器的方法
   public event MailMsgEventHandler MailMsg
   
{
      add
      
{
         mailMsgEventHandlerDelegate
=(MailMsgEventHandler)Delegate.Combine(mailMsgEventHandlerDelegate, value);;
      }

      
//将传入的事件处理器(value)从委托链表上移除
       remove
      
{
         mailMsgEventHandlerDelegate 
= (MailMsgEventHandler)Delegate.Remove(mailMsgEventHandlerDelegate, value);
      }

   }

   
//下面受保护的虚方法负责通知事件的登记对象,这里已经不是事件而是一个委托类型 的字段了
   
//有点难以理解
    protected virtual void onMailMsg(MailMsgEventArgs e)
    
{
       
if(mailMsgEventHandlerDelegate != null)
       
{
                    mailMsgEventHandlerDelegate(
this, e);
       }

    }

    
//在新电子邮件到达时被调用
    public void SimulateArrivingMsg(string from, string to, string Subject, string body)
    
{.}
}

posted on 2005-11-18 13:41  泽来  阅读(392)  评论(0编辑  收藏  举报