这两个概念真的是一个古董级的概念,不过我看了网上的教程,很多都是千篇一律的介绍,估计都是你抄我的我吵你的,不过确实有很多大佬名家介绍过这些东西。本人不是高手,书面语言说不来,干脆让我以自己的话说说这两个概念以及应用吧!希望和我一样的新手能加深印象。
委托
假如有三个果农摆地摊,一个卖苹果,一个卖橘子,另一个卖西瓜。每人都想在路边贴一张广告推销自己产品。这时候,不远处的商场说愿意免费帮他们发通知。而且三个人每个人的广告都不会落下。于是乎,货物被商场销售员统一发送通知到门口给路人,从而省去了果农们发通知这样的重复性工作。(也不知道这个例子合不合适)
从上面的例子可以看出,委托是一个负责管理方法运行的类型。当有一系列相似的任务和方法需要实施,就用委托。
1.如何实现委托
委托和类很相似,所以实现起来也差不太多。所有的委托都派生自Delegate,所以声明一个不返回任何结果的委托,可以这样。
delegate void MyDelegate(); //也可以声明一个返回结果或是带参数的委托
声明之后,要实例化委托。
static MyDelegate myDelegate;//静态(static)关键字不是必须的,只是为了调用方便。
上面的委托声明和实例化过程是不是很类是声明和实例化?只是委托实例化无需初始赋值。做完了上述步骤相当于创建了一个可以统一代发通知的商场。
有一个菜农带着他家里的的菜(卖苹果的通知 ,内容是“今天最新的苹果5出来了,快来买”),所以苹果果农的通知内容是这样的。
static void SellApple() { Console.WriteLine( "今天最新的苹果5出来了,快来买"); }
于是商场收到代发通知这个申请之后,就将通知放在“委托箱”。
static void Main(string[] args) { myDelegate += new MyDelegate(SellApple);
//注意是+=,这里的SellApple这个方法是作为一个参数,而不能带有括号 }
2.委托的方法累加
商场收到请求之后还在等。恰巧又有另外两个果农带着他们的通知来了。
static void SellOrange() { Console.WriteLine("又大又甜的橘子,不甜的不要钱"); } static void SellWaterMelon() { Console.WriteLine("快来尝试最新的切西瓜玩法"); }
所以商场又把通知全部扔到“委托箱”,就开始把委托箱里的通知全部张贴在了门口的通知栏。
static void Main(string[] args) { myDelegate += new MyDelegate(SellApple); myDelegate += new MyDelegate(SellOrange); myDelegate += new MyDelegate(SellWaterMelon); myDelegate.Invoke(); Console.Read(); }
大家赶紧看看他们发的通知吧!不过所有的游戏都是有规则的。这里的规则就是你的通知返回类型和参数类型都必须和商场规定的一致。否则不受理!
3.委托的方法移除
第二天那个西瓜果农急冲冲跑到商场,说要把通知撤掉,说是受了钓鱼岛事件的影响。结果刚好那通知因为通知栏不够大还没来得及贴出来。就扯下来了。挽回了摊子被砸的悲剧。
static void Main(string[] args) { myDelegate += new MyDelegate(SellApple); myDelegate += new MyDelegate(SellOrange); myDelegate += new MyDelegate(SellWaterMelon); myDelegate -= new MyDelegate(SellWaterMelon);//注意是-=,表示移除方法 myDelegate.Invoke(); Console.Read(); }
4.有返回值以及多个参数的委托
话说商场吸取了刚才的教训,把发布通知的方式升了一下级。全部采用电子显示屏,想发布多少通知就能发布多少,而不用每次都贴一张纸到通知栏上去。
class Program { /// <summary> /// 带参数和返回值的委托 /// </summary> /// <param name="note">通知内容</param> /// <returns>返回一个通知的文本</returns> public delegate string MyDelegate(string note); private static MyDelegate myDelegate; static void Main(string[] args) { myDelegate += new MyDelegate(SellFruit); Console.WriteLine( myDelegate.Invoke("apple"));
//这些Console.WriteLine就相当于统一发布消息的电子显示屏 Console.WriteLine( myDelegate.Invoke("orange")); Console.WriteLine( myDelegate.Invoke("watermelon")); Console.Read(); } static string SellFruit(string note) { string ret=""; switch(note) { case "apple": { ret= "今天最新的苹果5出来了,快来买"; break; } case "orange": { ret= "又大又甜的橘子,不甜的不要钱"; break; } case "watermelon": { ret= "快来尝试最新的切西瓜玩法"; break; } } return ret; } }
5.匿名函数的委托
有一天有人跑去商场发布一个这样的匿名通知,说是捡到了若干人民币,希望有人来领回去。
class Program { delegate void MyDelegate(); static void Main(string[] args) { MyDelegate mydele = delegate() { Console.WriteLine("失物招领!人民币若干,施主速度来领!"); }; mydele.Invoke(); Console.Read(); } }
这一的匿名方法委托用起来很方便,不知道有什么副作用没有。其实还可以在申明的委托后面直接赋值为方法名称。
delegate void MyDelegate(string strs); static void Main(string[] args) { MyDelegate my = Say; my.Invoke("hello!"); Console.Read(); } static void Say(string note) { Console.WriteLine(note); }
6.Lambda表达式委托
此一种委托实际上也属于匿名函数类型的委托。
class Program { delegate string MyDelegate(string strs); static void Main(string[] args) { //MyDelegate mydel = delegate(string x) { return x; }; // MyDelegate mydel = (string x)=> { return x; }; MyDelegate mydel = note => "官方说明:"+note; //最后一种是最简洁省略的写法 ,其中=>是拉姆达表达式, //左边的note是一个省去了关键字string的变量,用作输入,右边的是操作返回值 Console.WriteLine(mydel.Invoke("一个莫名其妙的通知")); Console.Read(); } }
其实委托还有很多种,这里只列出比较常见的几种,下次我们说说事件。
欢迎继续关注本人博客。