.net 之美读书笔记
来源:互联网 发布:firefox flash linux 编辑:程序博客网 时间:2024/05/20 07:13
委托与事件
委托
委托的定义
委托(delegate)可以理解为函数类型,实现了函数可以当作参数传递,使程序更加灵活。下面通过代码快速熟悉委托的使用顺序。
public delegate void GreetingDelegate(string name); class Program { //2.定义委托方法体 public static void EnglishGreeting(string name) { Console.WriteLine("Morning," + name); } public static void ChineseGreeting(string name) { Console.WriteLine("早上好," + name); } public static void GreetPeople(string name, GreetingDelegate markGreet) { //4.调用委托 markGreet(name); } static void Main(string[] args) { //3.将函数赋值给委托 GreetPeople("Jerry Zhao", EnglishGreeting); GreetPeople("番茄赵", ChineseGreeting); Console.ReadKey(); }
事件
事件(event):对委托的封装,保护委托不允许外部程序直接为委托赋值(会将已添加的委托丢掉)。
使用方法public event GreetingDelegate MarkGreet;
.Net事件模型
这里借助一个熟悉的例子讲诉事件模型。热水器烧水到95后,报警器报警,显示器显示。
/// <summary> /// 加热器 /// </summary> public class Heater { private int temperature; /// <summary> /// 型号 /// </summary> public string type = "RealFire 001"; /// <summary> /// 产地 /// </summary> public string area = "China Xian"; /// <summary> /// 委托 /// </summary> /// <param name="sender">被观察者(Heater)</param> /// <param name="e">传递到观察者的参数</param> public delegate void BoiledEnentHandler(object sender, BoiledEventArgs e); /// <summary> /// 初始化空函数,防止没有订阅值为null,调用报错 /// </summary> public event BoiledEnentHandler Boiled = (sender, e) => { }; /// <summary> /// 注意这里使用内部类,只是传递参数 /// 被观察着传入到观察者参数 /// </summary> public class BoiledEventArgs : EventArgs { public readonly int temperature; public BoiledEventArgs(int temperature) { this.temperature = temperature; } } /// <summary> /// 被观察者通知观察者方法 /// </summary> /// <param name="e">参数</param> protected virtual void OnBoiled(BoiledEventArgs e) { //#1多播委托 /* foreach(Delegate d in Boiled.GetInvocationList()) { BoiledEnentHandler boiled = (BoiledEnentHandler)d; boiled(this, e); } */ //#2异常处理,一个主题有多个订阅者。订阅者一个订阅者发出异常不应该阻塞其他订阅者 /* foreach (Delegate d in Boiled.GetInvocationList()) { BoiledEnentHandler boiled = (BoiledEnentHandler)d; try { boiled(this, e); } catch (Exception ex) { } } */ //#3超时处理,发布者不应这个通知订阅者,应采用一部调用 foreach (Delegate d in Boiled.GetInvocationList()) { BoiledEnentHandler boiled = (BoiledEnentHandler)d; boiled.BeginInvoke(this, e, null, null); } //Boiled(this, e); } /// <summary> /// </summary> public void BoilWater() { for (int i = 0; i <= 100; i++) { temperature = i; if (temperature > 95) { BoiledEventArgs e = new BoiledEventArgs(temperature); OnBoiled(e); } } } } /// <summary> /// 报警器 /// </summary> public class Alarm { public void MarkAlert(object sender, Heater.BoiledEventArgs e) { Heater heater = (Heater)sender; Console.WriteLine("Alarm:{0}-{1}", heater.area, heater.type); Console.WriteLine("Alarm:嘀嘀嘀,水已经{0}度", e.temperature); Console.WriteLine(); Thread.Sleep(500); } } /// <summary> /// 显示器 /// </summary> public class Display { public static void ShowMsg(object sender, Heater.BoiledEventArgs e) { Heater heater = (Heater)sender; if (e.temperature == 99) { Thread.Sleep(2000); } Console.WriteLine("Display:{0}-{1}", heater.area, heater.type); Console.WriteLine("Display:水已经{0}度", e.temperature); Console.WriteLine(); } } //调用 static void Main(string[] args) { Heater heater = new Heater(); Alarm alarm = new Alarm(); heater.Boiled += alarm.MarkAlert; heater.Boiled += Display.ShowMsg; heater.BoilWater(); Console.ReadKey(); }
委托进阶
利用上面的代码介绍下多播的进阶
* 1多播委托的调用
* 2异常处理,多播中异常处理
* 3超时处理,委托的异步调用成对出现 BeginXXX,EndXXX
阅读全文
0 0
- .net 之美读书笔记
- 团队之美读书笔记
- 《编程之美》读书笔记
- 《数学之美》读书笔记
- 《编程之美》读书笔记
- 编程之美读书笔记
- 架构之美读书笔记
- 数学之美读书笔记
- [读书笔记]互联网之美
- 《测试之美》--读书笔记
- 编程之美读书笔记
- 《数学之美》--读书笔记
- 数学之美-读书笔记
- 数学之美读书笔记
- 数学之美读书笔记
- 《数据之美》读书笔记
- 读书笔记-数学之美
- 《编程之美》读书笔记集锦
- IT英文文档下载
- 将Python脚本打包成可执行文件
- mongo 常用命令
- numpy常用API用法总结
- bootstrap basic style
- .net 之美读书笔记
- view的post方法
- 【C++ STL】深入解析神秘的 --- 仿函数
- jmeter正则表达式提取器相关操作讲解
- 大顶堆排序
- Windows x64免按F8加载驱动文件
- Android dialog不同的显示方式
- 设计模式(二十二)——享元模式
- List集合转Json