C#委托

声明委托类型:delegate <函数返回类型> <委托名> (<形参表>);

定义委托实例:<委托类型> <实例化名>=new <委托类型>(<注册函数>)  或  注册函数名;

匿名委托实例定义:<委托类型> <实例化名>=delegate(<形参表>){函数体}; 

注:匿名委托可使用lambda表达式

 

泛型委托类型定义:delegate <函数返回值类型,可使用泛型T1,T2等后面泛型参数中的一个> <委托名><T1,T2,T3...> (<形参表>)

泛型委托实例:<泛型委托类型><泛型参数> 

例:delegate T1 Test<T1,T2>(T2 t2);//定义有两个泛型(T1,T2)的委托,T2作为委托函数返回类型,T1作为委托函数参数类型

 

链式委托:链式委托也称作 '多播委托'

链式委托的实现需从委托的实现来说起:委托实例中存在多个成员变量,其中有3个重要的成员变量,一个指向所需执行的代码区域,一个是目标实例的引用(即所引用的函数,如函数是静态函数,则此值为null),另一个便是链式委托实现的关键,即下一个委托的引用 next ,委托进行调用时,如next不为空则会继续进行调用,这个next便是链式委托的具体实现。

例:

static void fun1(){ Console.WriteLine(1); }

static void fun2(){ Console.WriteLine(2); }

static void fun3(){ Console.WriteLine(3); }

delegate void Test();

Test test = fun1;

test += fun2;

test += fun3;

则输出结果则为:1 2 3

根据委托的实现则能如下定义委托:

Test t1 = fun1;

Test t2 = fun2;

Test t3 = fun3;

Test test = t1 + t2 + t3;

test();

输出结果为:1 2 3

Test test = t1 + t2 + t3;此方式仅是将 t1,t2,t3 委托中的函数列表赋值到新的委托中,并非引用

则:

Test t1 = fun1;

Test t2 = fun2;

Test t3 = fun3;

Test test = t1 + t2 + t3;

t1 += fun2;

test();

输出结果依然是:1 2 3

同理:

Test t1 = fun1;

Test test = t1;

t1 += fun2;

test();

输出结果是:1

因为委托之间的相互赋值仅仅是将委托中的函数列表赋值,由此可见C#中的委托类型应该将赋值符号 '=' 进行了重载

注:委托的调用时如多播委托带参数,则所有函数的参数都一样。委托的另一种调用方式:test.Invoke()

 

委托调用的顺序:委托调用时,委托中的函数列表按照增加的先后顺序依次执行,若想自己对函数的执行顺序进行排序,则可以使用:GetInvocationList()函数,其返回值为 Delegate[],

如:

Test test = fun1;

test += fun2;

Delegate[] data= test.GetInvocationList();

test = (Test)data[1];

test += (Test)data[0];

则输出结果为:2 1

注:若链式委托函数有返回值,则返回的为最后一个执行的函数的值,若需要所有的返回值,则可以通过上述的test.GetInvocationList()方法一个个的执行委托链中的函数来得到所有的返回值。

 

 

 

 

 

 

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值