C#事件与委托详解

来源:互联网 发布:windows能开发ios吗 编辑:程序博客网 时间:2024/06/16 03:24

http://blog.csdn.net/jamestaosh/article/details/4372172

这篇文章很详细的讲解了事件,委托的概念和相关的用法,虽然很长,但是全看完一遍真的会对初学者很有帮助


下面是我对其中的狗抓小偷例子的一点理解,并对其做了相应的修改


首先,狗发现小偷不能抓小偷,只能警报让主人来抓,所以这里狗是委托人,主人是被委托人,狗委托主人抓小偷,所以delegate定义在狗这里,狗有一个委托,  被委托的一方是主人.


在事件发生是,可以将委托人的引用传递给被委托人(也就是将狗的对象,传递给主人),这样被委托的对象就知道具体是哪个委托人传来的消息,好进行下面的各种操作...(例如有两个同级别的委托人,总不能接到委托人1的委托后,同事处理两个委托人的事件吧)

Animal.cs

using System;using System.Collections.Generic;using System.Text;using People;namespace Animal{        //警报事件参数  传递给被委托的对象    public class NumberOfThiefEventArgs : EventArgs    {        //传递给被委托对象的参数  这里可以随便定义参数的类型 (也就是主人)        public int numberOfThief;        //构造函数  初始化参数        public NumberOfThiefEventArgs(int number)        {            numberOfThief = number;                   }    }    class iAnimal    {        public string animalName;        //1.声明关于事件的委托;        public delegate void AlarmEventHandler(object sender, NumberOfThiefEventArgs e);               //3.编写引发事件的函数,这里使用自定义的警报事件参数        public  virtual void OnAlarm(NumberOfThiefEventArgs e)        {        }        public virtual void onChetui(object sender, EventArgs e)        {        }    }    //事件发送者    class Dog : iAnimal    {               //声明事件;        public event AlarmEventHandler AlarmEvent;        public override void OnAlarm(NumberOfThiefEventArgs e)        {            if (this.AlarmEvent != null)            {                Console.WriteLine("狗  狗: 有小偷进来了,汪汪~~~~~~~");                this.AlarmEvent(this, e);            }        }                //撤退        public override void onChetui(object sender, EventArgs e)        {            //获取到主人的实例            Zhuren zhuren = (Zhuren)sender;            Console.WriteLine("狗  狗:收到来自主人{0}的撤退命令,正在撤退~~~~~~~",zhuren.pName);        }        //搜查        public void onSearch(object sender, EventArgs e)        {            //获取到主人的实例            Zhuren zhuren = (Zhuren)sender;            Console.WriteLine("狗  狗:收到来自主人{0}的搜查命令,正在搜查~~~~~~~", zhuren.pName);        }    }    class Cat : iAnimal    {                public event AlarmEventHandler AlarmEvent;        public override void OnAlarm(NumberOfThiefEventArgs e)        {            if (this.AlarmEvent != null)            {                Console.WriteLine("猫  猫: 有小偷进来了,喵喵~~~~~~~");                this.AlarmEvent(this, e);            }        }               //撤退        public override void onChetui(object sender, EventArgs e)        {            //获取到主人的实例            Zhuren zhuren = (Zhuren)sender;            Console.WriteLine("猫  猫:收到来自主人{0}的撤退命令,正在撤退~~~~~~~", zhuren.pName);        }        //搜查        public void onSearch(object sender, EventArgs e)        {            //获取到主人的实例            Zhuren zhuren = (Zhuren)sender;            Console.WriteLine("猫  猫:收到来自主人{0}的搜查命令,正在搜查~~~~~~~", zhuren.pName);        }    }}


People.cs

using System;using System.Collections.Generic;using System.Text;using Animal;namespace People{    //主人    class Zhuren    {        //主人的名称        public string pName;        public delegate void ChetuiEventHandler(object sender, EventArgs e);   //声明委托        public event ChetuiEventHandler ChetuiEvent;        //声明事件        public delegate void SearchEventHandler(object sender, EventArgs e);        public event SearchEventHandler SearchEvent;        //触发撤退事件        void onChetuiEvent()        {            if(this.ChetuiEvent != null)            {                EventArgs e = new EventArgs();                ChetuiEvent(this, e);            }        }        //触发搜索事件        public void onSearchEvent()        {            if (this.SearchEvent != null)            {                EventArgs e = new EventArgs();                SearchEvent(this,e);            }        }        //抓小偷        void CatchThief(object sender, NumberOfThiefEventArgs e)        {            if (e.numberOfThief <= 1)            {                Console.WriteLine("主  人: 抓住了小偷!");            }            else            {                Console.WriteLine("主  人: 小偷太多 我打不过 撤退 ! 打110报警, 我家来了{0}个小偷!", e.numberOfThief);                this.onChetuiEvent();            }                    }        //处理小狗发来的警报        public void HostHandleDogAlarm(object sender, NumberOfThiefEventArgs e)        {            Dog dog = (Dog)sender;            Console.WriteLine("主  人: 收到小狗的委托请求!小狗的名字叫 {0}",dog.animalName);                        CatchThief(sender, e);        }        //处理小猫发来的警报        public void HostHandleCatAlarm(object sender, NumberOfThiefEventArgs e)        {            Cat cat = (Cat)sender;            Console.WriteLine("主  人: 收到小猫的委托请求!小猫的名字叫 {0}", cat.animalName);            CatchThief(sender, e);        }        public Zhuren()        {        }          }    class XiaoTou    {    }    }

Program.cs

using System;using System.Collections.Generic;using System.Text;using Animal;using People;namespace Delegate{    class Program    {        static void Main(string[] args)        {            Dog dog = new Dog();            dog.animalName = "Mr Dog";            Cat cat = new Cat();            cat.animalName = "Miss Cat";            Zhuren zhuren = new Zhuren();            zhuren.pName = "果冻";            //注册委托事件            //当小狗警报的时候 主人会执行HostHandleDogAlarm            dog.AlarmEvent += zhuren.HostHandleDogAlarm;            //当小猫警报的时候 主人会执行HostHandleCatAlarm            cat.AlarmEvent += zhuren.HostHandleCatAlarm;            //对小狗和小猫同时下达搜查命令            zhuren.SearchEvent += dog.onSearch;            zhuren.SearchEvent += cat.onSearch;            zhuren.onSearchEvent();                        //当前时间,从2015年8月21日23:59:55开始计时            DateTime now = new DateTime(2015, 8, 21, 23, 59, 55);            DateTime midnight = new DateTime(2015, 8, 22, 0, 0, 0);            //等待午夜的到来            Console.WriteLine("时间一秒一秒地流逝... ");            while (now < midnight)            {                Console.WriteLine("当前时间: " + now);                System.Threading.Thread.Sleep(1000); //程序暂停一秒                now = now.AddSeconds(1);                //时间增加一秒            }            //午夜零点小偷到达,看门狗引发Alarm事件            Console.WriteLine("月黑风高的午夜: " + now);            Console.WriteLine("小偷悄悄地摸进了主人的屋内... ");            //创建事件参数            NumberOfThiefEventArgs eDog = new NumberOfThiefEventArgs(1);            dog.OnAlarm(eDog);                       while (now < midnight.AddSeconds(5))            {                Console.WriteLine("当前时间: " + now);                System.Threading.Thread.Sleep(1000); //程序暂停一秒                now = now.AddSeconds(1);                //时间增加一秒            }            Console.WriteLine("又有3个小偷悄悄地摸进了主人的屋内... ");            NumberOfThiefEventArgs eCat = new NumberOfThiefEventArgs(3);            //告诉小猫小猫撤退              zhuren.ChetuiEvent += cat.onChetui;            //如果也想让小狗撤退 就加上下面这句            //zhuren.ChetuiEvent += dog.onChetui;                        cat.OnAlarm(eCat);                    }    }        }

控制台输出:



这里面对主人添加了两个代理,一个是搜查的代理,一个是撤退的代理,  搜查和撤退都是 猫和狗 才能做的事,所以在这两个事件中,主人成了委托人,猫和狗成了被委托人


delegate还有个好处就是可以通过 "+=" 和 "-+" 来动态添加和取消委托 


0 0