C# 委托与事件

C# 委托与事件

🐉

Action委托的使用

  1. 在一个函数里面调用另一个函数,只不过这个函数是当作参数传递进来的

  

微信图片20221207100248png

  1. 先设置一个 Action 类型的变量, 然后将函数存进变量, 然后运行这个变量,效果等同于运行这个函数,当然也可以传进去多个函数,然后在运行那个变量的时候,会一同执行
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
class Program
{
static Action function;
//传递参数👇
static Action <string,int,int>function2;
static void Main()
{
// function += Test1;
// function += Test2;
// function();
// 不需要时可以移除
// function -= Test2
//-------------------------------
function2 += PassParameter;
function2("result:",100,33);

}

static void Test1()
{
Console.WriteLine("Test1 had been writed 1");
}

static void Test2()
{
Console.WriteLine("Test2 had been writed 2");
}
static void PassParameter(string str,int a,int b)
{
Console.WriteLine(str+(a+b));
//如果不加括号 它会以为是字符类型,直接拼接了属于是
}
}

请留意:Main主函数必须是静态的

Action不支持返回值,于是有了Func


Func 实现带有返回值的委托调用

可以绑定带有返回值的方法 并且接受返回的结果

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
class Program
{
static Func<int, int, int> func1;
//其中第一个参数永远是其返回值,第二个第三个才是函数的类型
static void Main()
{
func1 += Test1;
int result = func1(100, 33);
//委托调度的时候 其实就是调度方法
Console.WriteLine(result);
func1 -= Test1;
//同样也支持移除
}

static int Test1(int a,int b)
{
return a + b;
}


}

请留意:如果+=多个值,只会返回最终的一个结果,以上全部覆盖了

Func最多支持16个参数的方法< result , 1 , … , 16?15 >,并且每个方法都有一个返回值

也可以当作参数传递👇

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
class Class
{
static void Main()
{

TestAll(test);
}

static void TestAll(Func<int,int,int> callBack)
{
Console.WriteLine("OK");

int result = callBack(100, 33);
Console.WriteLine(result);

}

static int test(int a ,int b)
{
return a + b;
}
}

如果是想在外部赋值应该在函数testAll参数callBack后 再设置两个参数

xpng


古老的委托👉delegate

rider64fiRzYKuQhnpng

老师评价:自由 但初学者觉得语法怪

我の评价:这不都是一样的么

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

class Class
{
delegate void Delegate();

private static Delegate delegate1;
static void Main()
{
delegate1 += test1;
delegate1 += test2;
delegate1();
Console.WriteLine("-------------------------------------");
delegate1 -= test1;
delegate1();

}

static void test1()

{
Console.WriteLine("this test 1");

}


static void test2()
{
Console.WriteLine("this test 2");
}

}

delegate 当作参数传入的例子

就像先声明一个数组,把每个方法存到里面

然后自定义一个函数,形参是个数组,然后调用的时候赋值

这个时候就能把数组内所有的元素都跑一遍

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
34
35

class Class
{
delegate void Delegate();

static Delegate delegate1;

static void Main()
{
delegate1 += test1;
delegate1 += test2;
// delegate1();
// Console.WriteLine("-------------------------------------");
// delegate1 -= test1;
// delegate1();
// 用一个方法传入另一个方法-----------------------------
container(delegate1);
}
    //-----------------------♥
static void container(Delegate d)
{
Console.WriteLine("tets~~~~~~~~~~~~~~");
d();
}

static void test1()
{
Console.WriteLine("this test 1");
}

static void test2()
{
Console.WriteLine("this test 2");
}
}

带有参数的

同样也只是计算最后一个函数

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
class Class
{
delegate int Delegate(int a , int b );
private static Delegate delegate1;

static void Main()
{
delegate1 += test1;
delegate1 += test2;
    //⭐
    int result = delegate1(3,4)
    //⭐

Console.WriteLine(result);
}

static void container(Delegate d1)
{
Console.WriteLine(d1);
}
static int test1(int a , int b )
{
return a + b;
}
static int test2(int a , int b )
{
return a * b;
}
}

留意:若是想打印出所有的方法应该在以下⭐处改动

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
34
35
class Class
{
delegate int Delegate(int a , int b );
private static Delegate delegate1;

static void Main()
{
delegate1 += test1;
delegate1 += test2;
// delegate1();
// Console.WriteLine("-------------------------------------");
// delegate1 -= test1;
// delegate1();
// 用一个方法传入另一个方法-----------------------------
        //⭐⭐⭐⭐ VARIABLE👇
foreach (Delegate VARIABLE in delegate1.GetInvocationList())
{
Console.WriteLine(VARIABLE(4,3));
}
}

static void container(Delegate d1)
{
Console.WriteLine(d1);
}
static int test1(int a , int b )
{

return a + b;
}
static int test2(int a , int b )
{
return a * b;
}
}

Event

实际上是对delegate的封装

rider64NdM1xepACzpng

在一个脚本对另一个脚本委托的注册

请留意调用的时候

一定要重新写个新函数,如上的RunEvent()


委托和事件的核心作用

  1. 解耦各个模块

  2. 避免直接去调度其他模块的方法

  3. 而是通过注册、移除注册的方式,来控制其他模块方法的调度

作者

发布于

2022-12-14

更新于

2022-12-19

许可协议