本文是对此文章的简化描述,用于口头表达:http://www.tracefact.net/tech/009.html
什么是委托
委托是引用类型,使用delegate关键字定义,本质上是一个类。是用来将方法作为方法的参数的。
委托在编译时会编译成类,作为类,我们在任何可以声明类的地方都可以声明委托。
委托这种把方法作为参数动态传递的方式,规避了程序中出现大量判断语句的问题,使得程序有更好的扩展性。
委托的使用步骤:定义-->赋值-->绑定额外的方法-->作为参数传递-->调用。
使用 += 和 -= 可以绑定解绑方法,调用时根据绑定顺序依次调用。
委托如果没有赋值,直接绑定会报错。
什么是事件
为了面向对象的封装,我们会倾向于把委托写在类中,但是它不能使用private(对其他类不可见),使用public又会被其他类随意的赋值操作破坏封装。于是 event 就作为一种对委托的封装(并不是真的封装)出现了,它使委托总是private的并限制只能使用 += 和 -= 访问符。
在编译时,事件会产生一个私有的委托变量,以及注册方法和注销方法(对应两种访问符),分别由add 和 remove开头。在add 方法内部,实际上调用了System.Delegate 中的 Combine() 静态方法,此方法用于将当前变量加入链表。
从委托事件到Observer设计模式
观察者模式是为了定义对象之间一种一对多的依赖关系,方便一个对象状态改变时,依赖它的对象会被自动告知并更新,起到解耦效果。
其中的一为被观察者,他包含着观察者关注的内容,当条件到达时,它会把数据发给观察者
而多是指所有的观察者,它们关注被观察者的某些内容,一旦观察者发出数据,它们会做出对应的反应。
根据以上说明和.net Framework 的编码规范,我们会这样实现观察者模式:
- 在被观察者中声明委托,命名以 EventHandler 结尾,返回值为 void ,参数输入一个 Object类型 一个 EventArgs 类型
- 然后声明一个事件,以委托去掉 EventHandler 命名。
- 声明一个 EventArgs 类型,作为委托的第二个参数,命名以 EventArgs 结尾,内部包含观察者关注的内容。
- 在观察者类型中写对应的用于注册的方法
- 在合适的地方注册方法,在合适的地方传递参数。