事件是什么?比如对于一个按钮,用户点击这个按钮之后程序就会给出反应,这就是事件。那委托是什么呢?委托是当用户点击按钮之后程序将要执行已经编写好的函数,不然怎么给出反应呢。这里说明一下,委托不是函数,但它可以指向一个函数,类似于C中的函数指针。
先简单介绍一下委托的基本用法
(1)委托用关键字delegate声明,有访问权限,返回值,委托名称,参数
(2)定义的委托没有方法体,直接以;结束
(3)以该委托名声明变量
(4)将声明的变量指向方法,注意:声明委托的返回值、参数类型和个数决定该委托只能指向以同样结构声明的函数
(5)调用:
class Program
{
//声明委托类型
public delegate int Mydele(int a, int b);
static void Main(string[] args)
{
//定义委托变量
Mydele d1, d2;
//为委托变量指向函数
d1 = new Mydele(sum);
d2 = new Mydele(muitly);
Console.WriteLine(deleTest(d1,3,5));
Console.WriteLine(deleTest(d2, 3, 5));
Console.Read();
}
public static int deleTest(Mydele d,int a,int b)
{
return d(a, b);
}
public static int sum(int a,int b)
{
return a + b;
}
public static int muitly(int a,int b)
{
return a * b;
}
}
通过这个例子不难发现,我们可以将方法作为变量传入函数中,对于接受委托变量的函数来说,它不关心这个委托到底是指向哪个方法的,就本例来说,它知道的就是这个委托指向的方法有一个int类型返回值,有2个int类型参数,函数体里面执行了一次这个委托指向的方法。简单的说就是将函数体里面的某一个功能委托给外部去实现,然后当做参数传进来(这个参数就是声明为delegate的变量)。
接下来看一下事件委托又是什么东西,简单的说就是:事件是委托的封装,委托的指向功能和调用功能由事件负责,在这里委托的作用就是告诉事件,你只能接受我已经定义好结构的函数,如返回值类型,参数类型和个数。看一下例子:
class Program
{
//声明委托类型
public delegate int Mydele(int a, int b);
//声明该委托的事件
public event Mydele MydeleHandle;
static void Main(string[] args)
{
//这里不再定义委托变量,直接通过其事件进行处理
MydeleHandle += sum;
//可以注册多个同结构的函数,但只有最后一个生效
//MydeleHandle += muitly;
//调用
int result=MydeleHandle(3, 5);
Console.WriteLine(result);
}
public static int sum(int a,int b)
{
return a + b;
}
public static int muitly(int a,int b)
{
return a * b;
}
}
最后再看一下自定义事件是怎么回事,注意,这里是才是实际应用,但前面的基础用法同样很重要,定义一个测试类:
class DelegateTest
{
private int xPoint;//X坐标
private int yPoint;//Y坐标
public delegate void XPointChangeDele(int x,int y);
public delegate void YPointChangeDele(int x,int y);
public event XPointChangeDele XChangeHandle;
public event YPointChangeDele YChangeHandle;
public int XPoint
{
get { return xPoint; }
set
{
xPoint = value;
/*
* 这里是重点,当x轴发生变化会执行以下event接收的用户自定义函数,
* 需要考虑若用户没有注册该事件的话这里是null,鲁莽调用会出现空
* 指针异常,所以设计的时候要考虑周到些,下同
*/
XChangeHandle?.Invoke(xPoint, yPoint);
}
}
public int YPoint
{
get { return yPoint; }
set
{
yPoint = value;
//重点
YChangeHandle?.Invoke(xPoint,yPoint);
}
}
}
测试:
class Program
{
static void Main(string[] args)
{
//初始化
DelegateTest dt = new DelegateTest();
//注册事件
dt.XChangeHandle += XChange;
dt.YChangeHandle += YChange;
//测试x轴与y轴变化时是否触发事件
dt.XPoint = 25;
dt.YPoint = 30;
Console.Read();
}
public static void XChange(int x,int y)
{
Console.WriteLine("X轴发生了变化,当前坐标为({0},{1})",x,y);
}
public static void YChange(int x,int y)
{
Console.WriteLine("Y轴发生了变化,当前坐标为({0},{1})", x, y);
}
}