事件是对象发送的消息以发信号通知操作的发生操作可能是由用户交互(例如鼠标单击)引起的也可能是由某些其他的程序逻辑触发的引发(触发)事件的对象叫做事件发送方捕获事件并对其作出响应的对象叫做事件接收方
在事件通信中事件发送方类不知道哪个对象或方法将接收到(处理)它引发的事件所需要的是在源和接收方之间存在一个媒介(或类似指针的机制)……NET Framework 定义了一个特殊的类型(Delegate)该类型提供函数指针的功能
与其他的类不同委托类具有一个签名并且它只能对与其签名匹配的方法进行引用这样委托就等效于一个类型安全函数指针或一个回调
C#中使用事件需要的步骤创建一个委托将创建的委托与特定事件关联(Net类库中的很多事件都是已经定制好的所以他们也就有相应的一个委托在编写关联事件处理程序——也 就是当有事件发生时我们要执行的方法的时候我们需要和这个委托有相同的签名)
编写事件处理程序利用编写的事件处理程序生成一个委托实例把这个委托实例添加到产生事件对象的事件列表中去这个过程又叫订阅事件
C#中事件产生和实现的流程定义A为产生事件的实例a为A产生的一个事件定义B为接收事件的实例b为处理事件的方法A由于用户(程序编写者或程序使用者)或者系统产生一个a事件(例如点击一个Button产生一个Click事件)
A通过事件列表中的委托对象将这个事件通知给B B接到一个事件通知(实际是Bb利用委托来实现事件的接收)
调用Bb方法完成事件处理
下面给出《C#入门经典》的例子并做一定的解释://====================Connectioncs===========
//事件定义也就是上面提到的A
//============================================
using System
using SystemTimers
namespace ChEx
{
/// <summary>
/// Connection 的摘要说明
/// </summary>
///
public delegate void MessageHandler(string messageText)//创建一个委托——步骤
public class Connection
{
public event MessageHandler MessageArrived//将创建的委托和特定事件关联在这里特定的事件为MessageArrived ——步骤*/
/*上面这语句值得注意的地方是 MessageArrived方法被关联到MessageHandler上后以后消息的传递就通过MessageHandler这个委托来实现所以如果要能接收这个消息就必须能支持MessageHandler这个委托也就是要有一个和委托一样的签名
private Timer pollTimer
public Connection()
{
// // TODO 在此处添加构造函数逻辑// pollTimer=new Timer()pollTimerElapsed+=new ElapsedEventHandler(CheckForMessage)}
public void Connect()
{ pollTimerStart()}
public void Disconnect()
{ pollTimerStop()}
public void CheckForMessage(object senderElapsedEventArgs e)
{ ConsoleWriteLine(Check for message)Random random=new Random()if((randomNext()==)&&(MessageArrived!=null))
{ MessageArrived(Hello Mum!)//程序编写者自己产生一个消息消息的内容为Hello Mum!
}
//====================Displaycs=========== //接收事件的类也就是上面提到的B //========================================= using Systemnamespace ChEx { /// <summary> /// Display 的摘要说明
/// </summary> public class Display { public Display()
{ // // TODO 在此处添加构造函数逻辑// }
public void DisplayMessage(string message) //a事件的最终处理函数即上面的Bb在main函数中我们会使用本函数实现一个委托实例并且添加到A的MessageArrived事件列表中——步骤 { ConsoleWriteLine(Message Arrived{}message)}
//====================Classcs================= //一个控制台可执行类主要是使用上面两个类的实例//============================================== using System
namespace ChEx { /// <summary> /// Class 的摘要说明
/// </summary> class Class { /// <summary> /// 应用程序的主入口点
/// </summary> [STAThread] static void Main(string[] args)
{ // // TODO 在此处添加代码以启动应用程序// Connection myConnection=new Connection()Display myDisplay=new Display()myConnectionMessageArrived+=new MessageHandler(myDisplayDisplayMessage)//把委托添加到当前A的事件列表中——步骤和步骤 myConnectionConnect()
ConsoleReadLine()
}
}
注程序代码中事件定义部分委托定义部分的相关知识可以参看MSDN值得注意的代码public delegate void MessageHandler(string messageText)//委托定义
public event MessageHandler MessageArrived//定义一个事件并且关联到一个委托上
myConnectionMessageArrived+=new MessageHandler(myDisplayDisplayMessage)//产生一个委托实例并通过+=运算符号添加到事件列表中 +=运算符号在这里非常的有用