C#基础知识2:基于委托概念产生的事件机制

1、定义

如果你知道观察者模式,那么在.NET框架中,微软为我们提供了一个现成的事件机制实现了观察者模式。是基于委托的后期绑定机制。也就是说,当一个类型的状态发生变化,或者它检测到某个状态发生变化,就会通过事件机制通知给对应的对象

观察者模式:定义对象间一种一对多的依赖关系,使得当每一个对象改变状态,则所有依赖于它的对象都会得到通知并自动更新

相关基础

关键字:evnet

是C#中关键字的访问修饰符,表明后续修饰的类型是一个事件

基类:EventArgs

事件的参数,事件触发后,可以通过该基类传递自定义类型的参数

事件的应用场景

  • 通知功能
    • 举个例子:当一个服务器需要监听Socket连接时,需要启动一个监听线程,当这个线程监听到有客户端接入之后,会通知相应的应用层类进行对应的处理,这里就可以应用到事件中的通知功能,可以注册多个事件处理,谁先注册,谁先执行

C#基础知识2:基于委托概念产生的事件机制_第1张图片

2、实现方式

实现方式一:通过EventHandler实现事件注册

原型:.NET中提供了一个EventHandler事件,这个事件本质上其实就是一个委托

public delegate void EventHandler<TEventArgs>(object sender, TEventArgs e)
  • Object sender
    • 事件源的实例
      • 一般是某个事件触发源的实例
      • 在事件接受的类中可以接收到,并且可用as进行转换
  • TEventArgs e
    • 事件的参数(是一个泛型,可自定义
      • 可以直接传入一个类型的实例
      • 也可以通过自定义一个针对某个实例封装好的***Args类型(如下例)
// Socks5服务器等待Tcp服务器有客户端接入时,通知并将客户端传递给Socks5服务器
// 事件参数
public class ClientEventArgs : EventArgs
{
    public Client Client { get; private set; }
    public ClientEventArgs(Client client)
    {
        Client = client;
    }
}

// 事件的触发者
public class TcpServer
{
    // 一个事件,当有客户端接入的时候的通知事件
    public event EventHandler<ClientEventArgs> onClientConnected = delegate { };
    
    void WhenClientConnected()
    {
        // …………Do Something…………
        
        Client f = new Client();
        // 将一个Client实例通过ClientArgs的EventArgs传递给事件接收者
        onClientConnected(this, new ClientEventArgs(f));
     }
}

// 事件的接收者
public class socksServer
{
    public socksServer()
    {
        Private Tcpserver Tcps = new TcpServer();
        // 通过一个方法订阅这个事件,当这个事件被触发的时候,就会执行这个函数
        Tcps.onClientConnected += _server_onClientConnected;
    }
    
    void _server_onClientConnected(object sender, ClientEventArgs e)
    {
        Client client = e.Client;
    }
}

实现方式二:异步回调

通过C#所提供的委托机制,.NET为程序员们提供了非常多现成的委托类型,其中就有异步回调

一个.NET提供的类型TcpListener中,有一个BeginAcceptTcpClient方法,这个方法用来再有Tcp客户端接入的时候,通过异步回调的方式调用客户端的函数

  • 函数声明如下
public IAsyncResult BeginAcceptSocket(AsyncCallback callback, object state);
  • 使用如下:
// 一个自定义的TcpServer,当有Tcp客户端接入之后,做出相应处理;
public TcpServer()
{
    p = new TcpListener(ip, port);
    p.BeginAcceptSocket(new AsyncCallback(AcceptClient), p);   // 调用后,不会在此停等,直到有Socket客户端接入
}

void AcceptClient(IAsyncResult res)
{
    // 当Tcp客户端接入后,才会调用到该函数;
}

BeginAcceptSocket是.NET框架提供的方法,可以参照这个函数,设计自己对应的异步回调方法的接口

你可能感兴趣的:(C#基础知识)