事件的本质---特殊的多路广播委托
定义事件:
事件访问修饰符一般为public 定义为公共类型可以使事件对其他类可见
事件定义中还包括委托类型,既可以是自定义委托类型也可以是EventHandler(预定义)
运用"+="运算符来订阅事件,运用"-="运算符来取消订阅事件
例:自定义委托事件
1 class HelloWorld 2 { 3 //定义委托类型 4 public delegate void Marry(string msg); 5 //使用自定义委托类型定义事件 6 public event Marry MarryEvent; 7 //发出事件 8 public void News(string msg) 9 { 10 //判断是否绑定了事件处理方法 11 if(MarryEvent!=null) 12 { 13 //触发事件 14 MarryEvent(msg); 15 } 16 17 } 18 static void Main(string[] args) 19 { 20 //初始化新郎官对象 21 HelloWorld helloWorld=new HelloWorld(); 22 //实例化朋友 23 Friend zhangsan=new Friend("Zhangsan"); 24 Friend lishi=new Friend("Lishi"); 25 Friend zhaoliu=new Friend("Zhaoliu"); 26 //订阅事件 27 helloWorld.MarryEvent += new Marry(zhangsan.SendMessage); 28 helloWorld.MarryEvent += new Marry(lishi.SendMessage); 29 helloWorld.MarryEvent += new Marry(zhaoliu.SendMessage); 30 //发出通知 31 helloWorld.News("他要结婚了,到时来"); 32 Console.WriteLine("---------------------------------------"); 33 //张三取消订阅 34 helloWorld.MarryEvent -= new Marry(zhangsan.SendMessage); 35 //发出通知 36 helloWorld.News("他要结婚了,到时来"); 37 Console.ReadKey(); 38 } 39 } 40 41 class Friend 42 { 43 //字段 44 public string Name; 45 public Friend(string name) 46 { 47 Name = name; 48 } 49 //事件处理函数,该函数需要符合Marry委托定义 50 public void SendMessage(string message) 51 { 52 //输出信息 53 Console.WriteLine(message); 54 //对事件做出处理 55 Console.WriteLine("{0}收到了到时准时参加",Name); 56 } 57 58 }
例:预定义委托事件
1 class HelloWorld 2 { 3 //使用自定义委托类型定义事件 4 public event EventHandler MarryEvent; 5 //发出事件 6 public void News(string msg) 7 { 8 //判断是否绑定了事件处理方法 9 if(MarryEvent!=null) 10 { 11 Console.WriteLine(msg); 12 //触发事件 13 MarryEvent(this,new EventArgs()); 14 } 15 16 } 17 static void Main(string[] args) 18 { 19 //初始化新郎官对象 20 HelloWorld helloWorld=new HelloWorld(); 21 //实例化朋友 22 Friend zhangsan=new Friend("Zhangsan"); 23 Friend lishi=new Friend("Lishi"); 24 Friend zhaoliu=new Friend("Zhaoliu"); 25 //订阅事件 26 helloWorld.MarryEvent += new EventHandler(zhangsan.SendMessage); 27 helloWorld.MarryEvent += new EventHandler(lishi.SendMessage); 28 helloWorld.MarryEvent += new EventHandler(zhaoliu.SendMessage); 29 //发出通知 30 helloWorld.News("他要结婚了,到时来"); 31 Console.WriteLine("---------------------------------------"); 32 //张三取消订阅 33 helloWorld.MarryEvent -= new EventHandler(zhangsan.SendMessage); 34 //发出通知 35 helloWorld.News("他要结婚了,到时来"); 36 Console.ReadKey(); 37 } 38 } 39 40 class Friend 41 { 42 //字段 43 public string Name; 44 public Friend(string name) 45 { 46 Name = name; 47 } 48 //事件处理函数,该函数需要符合Marry委托定义 49 public void SendMessage(object s,EventArgs e) 50 { 51 //对事件做出处理 52 Console.WriteLine("{0}收到了到时准时参加",Name); 53 } 54 55 }
运行结果:
例:EventArgs扩展
1 //自定义事件类型并使其带有事件数据 2 public class EventMsg : EventArgs 3 { 4 public string Msg; 5 6 public EventMsg(string msg) 7 { 8 Msg = msg; 9 } 10 } 11 12 13 class HelloWorld 14 { 15 //使用自定义委托类型定义事件 16 public event EventHandler MarryEvent; 17 //发出事件 18 public void News(string msg) 19 { 20 21 //判断是否绑定了事件处理方法 22 if(MarryEvent!=null) 23 { 24 //触发事件 25 MarryEvent(this, new EventMsg(msg)); 26 } 27 28 } 29 static void Main(string[] args) 30 { 31 //初始化新郎官对象 32 HelloWorld helloWorld=new HelloWorld(); 33 //实例化朋友 34 Friend zhangsan=new Friend("Zhangsan"); 35 Friend lishi=new Friend("Lishi"); 36 Friend zhaoliu=new Friend("Zhaoliu"); 37 //订阅事件 38 helloWorld.MarryEvent += new EventHandler(zhangsan.SendMessage); 39 helloWorld.MarryEvent += new EventHandler(lishi.SendMessage); 40 helloWorld.MarryEvent += new EventHandler(zhaoliu.SendMessage); 41 //发出通知 42 helloWorld.News("他要结婚了,到时来"); 43 Console.WriteLine("---------------------------------------"); 44 //张三取消订阅 45 helloWorld.MarryEvent -= new EventHandler(zhangsan.SendMessage); 46 //发出通知 47 helloWorld.News("他要结婚了,到时来"); 48 Console.ReadKey(); 49 } 50 } 51 52 class Friend 53 { 54 //字段 55 public string Name; 56 public Friend(string name) 57 { 58 Name = name; 59 } 60 //事件处理函数,该函数需要符合Marry委托定义 61 public void SendMessage(object s,EventArgs e) 62 { 63 //对事件做出处理 64 Console.WriteLine("{0}收到了到时准时参加",Name); 65 } 66 67 }
在VS中可以用F12查看EventHandler的定义
public delegate void EventHandler(object sender, EventArgs e);
(1)该委托返回类型是void因此实例化委托类型的方法也要满足这点
(2)第一个参数sender负责保存对触发事件对象的引用,其类型为object
(3)第二个参数e保存事件数据,EventArgs类也是.NET类库中定义的类,它不保存任何火数据