C#关于事件的几个好例子
#region
// 定义BoiledEventArgs类,传递给Observer所感兴趣的信息
public class BoiledEventArgs : EventArgs
{
public readonly int temperature;
public BoiledEventArgs(int temperature)
{
this.temperature = temperature;
}
} //热水器
public class Heared {
public string type = "RealFire 001"; // 添加型号作为演示
public string area = "China Xian"; // 添加产地作为演示
private int temperature;
public delegate void BoidHandler(Object sender, BoiledEventArgs e); //声明委托
public event BoidHandler BoidEvent; //声明事件 // 可以供继承自 Heared的类重写,以便继承类拒绝其他对象对它的监视
protected virtual void OnBoiled(BoiledEventArgs e)
{
if (BoidEvent != null)
{ // 如果有对象注册
BoidEvent(this, e); // 调用所有注册对象的方法
}
}
//烧水
public void BoilWater() {
for (int i = ; i < ; i++)
{
temperature = i;
if (temperature>)
{
//建立BoiledEventArgs 对象。
BoiledEventArgs e = new BoiledEventArgs(temperature);
OnBoiled(e); // 调用 OnBolied方法
}
}
}
}
// 警报器
public class Alarm
{
public void MakeAlert(Object sender, BoiledEventArgs e)
{
Heared heater = (Heared)sender; //这里是不是很熟悉呢?
//访问 sender 中的公共字段
Console.WriteLine("Alarm:{0} - {1}: ", heater.area, heater.type);
Console.WriteLine("Alarm: 嘀嘀嘀,水已经 {0} 度了:", e.temperature);
Console.WriteLine();
}
} // 显示器
public class Display
{
public static void ShowMsg(Object sender,BoiledEventArgs e)
{ //静态方法
Heared heater = (Heared)sender;
Console.WriteLine("Display:{0} - {1}: ", heater.area, heater.type);
Console.WriteLine("Display:水快烧开了,当前温度:{0}度。", e.temperature);
Console.WriteLine();
}
}
class Program
{
static void Main()
{
Heared heater = new Heared();
Alarm alarm = new Alarm(); heater.BoidEvent += alarm.MakeAlert; //注册方法
heater.BoidEvent += (new Alarm()).MakeAlert; //给匿名对象注册方法
heater.BoidEvent += new Heared.BoidHandler(alarm.MakeAlert); //也可以这么注册
heater.BoidEvent += Display.ShowMsg; //注册静态方法 heater.BoilWater(); //烧水,会自动调用注册过对象的方法
}
}
#endregion
输出为:
Alarm:China Xian - RealFire 001:
Alarm: 嘀嘀嘀,水已经 96 度了:
Alarm:China Xian - RealFire 001:
Alarm: 嘀嘀嘀,水已经 96 度了:
Alarm:China Xian - RealFire 001:
Alarm: 嘀嘀嘀,水已经 96 度了:
Display:China Xian - RealFire 001:
Display:水快烧开了,当前温度:96度。
// 省略 ...
Observer设计模式中主要包括如下两类对象:
- Subject:监视对象,它往往包含着其他对象所感兴趣的内容。在本范例中,热水器就是一个监视对象,它包含的其他对象所感兴趣的内容,就是temprature字段,当这个字段的值快到100时,会不断把数据发给监视它的对象。
- Observer:监视者,它监视Subject,当Subject中的某件事发生的时候,会告知Observer,而Observer则会采取相应的行动。在本范例中,Observer有警报器和显示器,它们采取的行动分别是发出警报和显示水温。
在本例中,事情发生的顺序应该是这样的:
- 警报器和显示器告诉热水器,它对它的温度比较感兴趣(注册)。
- 热水器知道后保留对警报器和显示器的引用。
- 热水器进行烧水这一动作,当水温超过95度时,通过对警报器和显示器的引用,自动调用警报器的MakeAlert()方法、显示器的ShowMsg()方法。
类似这样的例子是很多的,GOF对它进行了抽象,称为Observer设计模式:Observer设计模式是为了定义对象间的一种一对多的依赖关系,以便于当一个对象的状态改变时,其他依赖于它的对象会被自动告知并更新。Observer模式是一种松耦合的设计模式
.Net Framework的编码规范:
- 委托类型的名称都应该以EventHandler结束。
- 委托的原型定义:有一个void返回值,并接受两个输入参数:一个Object 类型,一个 EventArgs类型(或继承自EventArgs)。
- 事件的命名为 委托去掉 EventHandler之后剩余的部分。
- 继承自EventArgs的类型应该以EventArgs结尾。
再做一下说明:
- 委托声明原型中的Object类型的参数代表了Subject,也就是监视对象,在本例中是 Heated(热水器)。回调函数(比如Alarm的MakeAlert)可以通过它访问触发事件的对象(Heated)。
- EventArgs 对象包含了Observer所感兴趣的数据,在本例中是temperature。
C#关于事件的几个好例子的更多相关文章
- Android 属性动画监听事件与一个菜单的例子
简单监听事件 ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 3 ...
- js——事件冒泡与捕获小例子
布局代码 #outer{ width: 300px; height: 300px; background: red; } #inner{ width: 200px; height: 200px; ba ...
- C#利用事件与委托进行窗体间传值简单小例子
本篇博客是利用C#委托与事件进行窗体间传值的简单小例子 委托与事件的详细解释大家可以参照张子阳的博客: http://www.tracefact.net/CSharp-Programming/Dele ...
- 谈谈JS的观察者模式(自定义事件)
呼呼...前不久参加了一个笔试,里面有一到JS编程题,当时看着题目就蒙圈...后来研究了一下,原来就是所谓的观察者模式.就记下来...^_^ 题目 [附加题] 请实现下面的自定义事件 Event 对象 ...
- JS 的事件委托机制
以前写上图所示的鼠标点击触发事件,一般都是用如下所示的给每一个表示列表的标签绑定一个click事件(演示用的例子的框架是React): 毫无疑问,这样是比较繁琐的,以后维护修改改个函数名什么的还不方便 ...
- jQuery-1.9.1源码分析系列(十) 事件系统——事件委托
jQuery的事件绑定有几个比较优秀的特点: 1. 可以绑定不限数量的处理函数 2. 事件可以委托到祖先节点,不必一定要绑到对应的节点,这样后添加的节点也照样能被处理. 3. 链式操作 下面主要分析事 ...
- 你真的了解DOM事件么?
你真的了解DOM事件么? 我们大家都知道,人与人之间的交流可以通过语言,文字,肢体动作,面部微表情等,但是你知道Javascript和HTML之间是通过什么进行交互的么?你又知道Javascript和 ...
- Android Touch事件传递机制 一: OnTouch,OnItemClick(监听器),dispatchTouchEvent(伪生命周期)
ViewGroup View Activity dispatchTouchEvent 有 有 有 onInterceptTouchEvent 有 无 无 onTouchEvent 有 有 有 例 ...
- image的加载事件(onload)和加载状态(complete)
之前做过这样一个需求,要让商家页的商家图片按照图片外面box的大小等比例缩放.之前的想法是在页面中先输出图片的src,然后在页面底部初始化js,然后在js中写相应的可以使图片按照box的大小等比例缩放 ...
随机推荐
- iOS 7 改变Status Bar 颜色
Set the UIViewControllerBasedStatusBarAppearance to NO in the Info.plist. In ViewDidLoad method or a ...
- java中return和continue区别
编程语言大多是想通的,当然java也不例外,下面的在其他编程语言也是相同的道理. return与continue的区别 先看代码哦 class demo2 { public static void m ...
- 键盘code码速查表
键盘 Key Code对照表 字母和数字键的键码值(keyCode) 按键 键码 按键 键码 按键 键码 按键 键码 A 65 J 74 S 83 1 49 B 66 K 75 T 84 2 50 C ...
- Beauty of Array(思维)
Beauty of Array Time Limit: 2 Seconds Memory Limit: 65536 KB Edward has an array A with N integ ...
- android面试题之五
二十六.什么情况会导致Force Close ?如何避免?能否捕获导致其的异常? 抛出运行时异常时就会导致Force Close,比如空指针.数组越界.类型转换异常等等. 捕获:可以通过logcat查 ...
- Linux 下mysql修改数据库存放目录方法和可能遇到的问题
MySQL版本:5.6.23-enterprise-commercial-advanced ,使用rpm安装linux:Red Hat Enterprise Linux Server release ...
- List小练习
功能:创建链表节点,删除节点,顺序打印,不改变原结构的情况下分别用STL中的stack实现逆序打印和利用函数递归打印 代码如下: //链表问题struct ListNode { int m_nV ...
- html中的表格 bootstrap-table
1 bootstrap-table 官网: http://bootstrap-table.wenzhixin.net.cn/ 2
- html 调用 activeX(c++)
1.新建MFC ActiveX 2.添加方法 3.找到add函数编写代码 4.在test.idl中找到最后一个uuid 5.编译工程,会自动注册控件 6.html中的代码 <html> & ...
- android的reference table的问题
写得android程序总是崩溃,感觉像是内存泄露,但是检查代码发现该释放的都释放了.最终无奈,删除了接口函数中的调用,只使用下面的测试代码. JNIEXPORT jboolean JNICALL Ja ...