委托:让方法能够跟简单对象同样做为参数进行传递,也就是将方法做为参数进行封装。
方法:本质就是代码段数组
其实也好理解,目的就是为了封装,多态,既然简单对象如int i能够作为参数传递,那么语句代码段应该也能够做为参数传递。测试
委托之于方法就像父类之于子类
委托就是一个抽象化的方法类型定义
(目的也是为了方便方法做为参数传递,这样想,又有点泛型的感受)code
简单对象抽象一次出现了类型
简单类型抽象一次出现了泛型
简单方法抽象一次出现了委托htm
委托在IL中实际上就是一个class对象
public delegate void MyDelegate(); public static void test() { MyDelegate d = null; MyDelegate d1 = new MyDelegate(obj.Method); MyDelegate d2 = new MyDelegate(obj.Method); d += d1; d += d2; }
public delegate void MyDelegate(); public static void test() { MyDelegate d = null; d += obj.Method; d += obj.Method; }
若是上述理解没错的话,再加上我简单的测试了下,Add watch
两个d,委托d的GetInvocation
是一致的,那么所谓委托链跟多播委托在上述的用法上的没区别的。blog
委托链包装的方法会顺序被执行,若是委托链中被调用的委托抛出一个异常,这样链中的后续全部对象都不会被调用。事件
直接调用这个委托链(委托链自己就是个委托)委托的返回值为非void
的话,只有最后一个返回值会被保留,以前的都舍弃。原型链
若需解决上述问题,经过调用Delegate.GetInvocation
方法来获取委托链对象数组,显示调用链中的每个委托。get
Delegate.GetInvocation
返回一个Delegate
引用构成的数组,注意是引用,数组中的每一个对象指向一个委托对象。而指向的这个委托对象又能够有本身的委托引用数组,一直下去,造成一条委托链,是否是有点相似js的原型链
。
委托变量能够在定义该委托变量的类外部直接调用和用=赋值,一旦向类外部公开(委托变量修饰符为public)委托变量,何时调用这个委托变量,你是没法控制的。
事件则不一样,在定义事件变量的类外部只能添加或移除处理程序(方法,本质也是委托),而事件在何时,什么条件下执行只能在定义事件变量的类内部定义。
事件可看做委托的一个特殊实例。叫实例貌似不太恰当,由于事件自己没有方法挂载,也就是没有实现。叫“子委托” 或许合适点,由于委托其实就是class
,那么事件叫委托的“子类”也何尝不可。
事件之于委托貌似又相似属性之于字段
+= -=对应于get set
欢迎讨论~
感谢阅读~
我的公众号: