事件是一种多播委托实例
事件处理函数是委托实例(事件)指向的函数
事件触发是调用委托实例
声明委托格式(决定了事件处理函数的格式)(一般是全局声明)
名称带Handler
事件的创建:用event关键字来创建事件(这个事件可以订阅某个格式的委托)
/*event关键字的意义是保证该委托实例不能在外部被随意触发。https://blog.youkuaiyun.com/weixin_42163773/article/details/84303784*/
事件的订阅:让这个事件+或-某个事件处理函数。
一个沙雕时钟
//全局范围声明委托格式 这里的格式只是逻辑意义上的
public delegate void ClockSoundHandler();
public delegate void AlarmHandler();
class Clock
{
//创建事件
public event ClockSoundHandler TickEvent;
public event ClockSoundHandler TockEvent;
public event AlarmHandler TimeUpEvent;
//时钟时间
private static int Sec { get; set; }
private static int Min { get; set; }
private static int Hour { get; set; }
//响铃时间
public int s;
public int m;
public int h;
//构造函数
public Clock(int h,int m,int s)
{
Sec = 0;
Min = 0;
Hour = 0;
this.s = s;
this.m = m;
this.h = h;
//事件订阅
TickEvent += onTick;
TockEvent += onTock;
TimeUpEvent += alarm;
}
//事件处理函数
void onTick() {Console.WriteLine("~~~~~~~Tick~~~~~~~");}
void onTock() { Console.WriteLine("~~~~~~~Tock~~~~~~~"); }
void alarm() { Console.WriteLine("-----Time's Up-----"); }
//开始工作
public void StartWork()
{
while (Sec+1 != s || Min != m || Hour != h)
{
Sec += 1;
if (Sec == 60 && Min != 60)
{
Min += 1;
Sec = 0;
TockEvent();
Thread.Sleep(1000);
continue;
}
else if (Sec == 60 && Min == 60)
{
Hour += 1;
Sec = Min = 0;
TockEvent();
Thread.Sleep(1000);
continue;
}
TickEvent();
Thread.Sleep(1000);
}
TimeUpEvent();
}
}
static void Main(string[] args)
{
Clock clock1 = new Clock(0,0,5);
clock1.StartWork();
Console.ReadKey();
}
除了用户自定义的委托之外,系统还未用户提供了一个内置的委托类型:
Action和Func
Action委托:
该委托引用了一个void返回类型的方法
没有返回值的,但是可以通过在Action后面声明泛型来指定方法的参数类型。
//定义了一个委托类型
//该类型可以指向一个没有返回值,有一个int类型参数的方法
Action<int> a;
//类似的
//定义了一个委托类型
//该类型可以指向一个没有返回值,有一个string类型参数的方法
Action<string> b;
//该类型可以指向一个没有返回值,但是又两个参数:int和string的方法
Action<int, string> c;