【C#基础教程】第二十章、事件

news2024/11/26 15:48:52

目录

事件

1.事件

2.扩展EventArgs类


事件

1.事件

 事件的组成:事件由事件发布者和事件订阅者组成。事件内包含一个私有委托。

  • 当事件发布时,事件发布者会发布消息、而事件订阅者会接受到事件已发生的通知,并作出相应的处理。
    • 其中,触发事件的对象称为事件发布者,捕获事件并对其做出处理的对象称为事件订阅者。
具有一个事件的类的结构和术语

 

  事件的意义:很多程序都有同一种需求,当一个特定的程序事件发生时,程序的其他部分可以得到该事件已经发生的通知。

  • 发布者类定义了一系列程序的其他部分可能感兴趣的事件。其他类可以注册,以便在这些事件发生时收到发布者的通知。这些订阅者通过向发布者提供一个方法来注册以获得通知。当事件发生时,发布者触发事件,然后执行订阅者提供的所有事件。
  • 用生活中的事件举例:当我们听说哪里发生了某件事的时候,可能会对这件事采取某种措施。例如,我们看见宠物碗里没水了,我们需要向里面添加水。在C#中,我们看见宠物碗里没水了会被当成“事件”,而添加水则是对事件做出的响应。 

  事件的定义:事件建立在委托之上。且事件与定义类成员非常相似,仅需在其基础上使用event关键字即可。

  使用自定义委托类型定义事件的语法:

                访问修饰符 event 委托类型 事件名;

  使用.NET类库定义事件的语法:

                访问修饰符 event EventHandler 事件名;

  订阅事件的语法:

                发布者对象.事件名+=new 委托名(订阅者对象.处理事件方法名);

  取消订阅事件的语法:

                发布者对象.事件名-=new 委托名(订阅者对象.处理事件方法名);

  执行处理事件的语法:

                发布者对象.发出事件(参数);

   使用事件的要求:

  • 定义事件的访问修饰符一般为public。主要是为了方便事件订阅者进行订阅和取消操作
  • 委托类型既可以是自定义的委托类型,也可以是.NET类库中的EventHandler。

  使用事件: 

1.使用自定义委托类型定义事件

//宠物碗类,充当事件发布者
public class PetBowl
{
    //自定义委托
    public delegate void WaterHandler(string water);
    //使用自定义委托类型定义事件
    public event WaterHandler WaterEvent;
    
    //发出事件
    public void WaterDry(string water)
    {
        //判断是否绑定了事件处理方法
        if(WaterEvent!=null)
        {
            WaterEvent(water);
        }
    }
}
//主人类,充当事件订阅者
public class Master
{
    //字段
    public string Name;
    //构造函数
    public Master(string name)
    {
        Name = name;
    }
    //处理事件方法,该方法需要符合WaterHandler委托的定义
    public void FullWater(string water)
    {
        //对事件做出处理
        Console.WriteLine("{0}开始给宠物碗添加了{1}",this.Name,water);
    }
}
public class Program
{
    static void Main(string[] args)
    {
        //初始化宠物碗对象(事件发布者)
        PetBowl petBowl = new PetBowl();
        //实例化主人(事件订阅者)
        Master masterOne = new Master("憨憨一号");
        Master masterTwo = new Master("憨憨二号");
        Master masterThree = new Master("憨憨三号");

        //使用+=来订阅事件
        petBowl.WaterEvent+=new WaterHandler(masterOne.FullWater);
        petBowl.WaterEvent+=new WaterHandler(masterTwo.FullWater);

        //发出通知,此时只有订阅了事件的对象才能收到通知
        petBowl.WaterDry("牛奶");
        //使用+=来订阅事件
        petBowl.WaterEvent+=new WaterHandler(masterThree.FullWater);
        //使用-=来取消订阅事件
        petBowl.WaterEvent-=new WaterHandler(masterTwo.FullWater);
        //发出通知
        petBowl.WaterDry("水");
    }
}

2.使用.NET类库中的委托类型定义事件

//事件发布者
public class PetBowl
{
    //使用.NET类库中的委托类型定义事件
    public event EventHandler WaterEvent;
    //发布事件
    public void WaterDry(string water)
    {
        if(WaterEvent!=null)
        {
            //触发事件
            WaterEvent(this,new EventArgs(),water);
        }
    }
}
//事件订阅者
public class Master
{
    //字段
    public string Name;
    //构造函数
    public Master(string name)
    {
        Name=name;
    }
    //处理事件
    public void FullWater(object one,EventArgs e,string water)
    {
        Console.WriteLine("{0}向宠物碗中添加了{1}",this.Name,water);
    }
}
public class Program
{
    static void Main(string[] args)
    {
        //实例化事件发布者
        PetBowl petBowl=new PetBowl();
        //实例化事件订阅者
        Master masterOne = new Master();
        Master masterTwo = new Master();
        //订阅事件
        petBowl.WaterEvent += new EventHandler(masterOne.FullWater);
        petBowl.WaterEvent += new EventHandler(masterTwo.FullWater);
        //取消订阅事件
        petBowl.WaterEvent -= new EventHandler(masterTwo.FullWater);

        //触发事件
        petBowl.WaterDry("水");
    }
}

2.扩展EventArgs类

        当我们使用.NET类库中的委托类型定义事件时,我们会发现EventHandler只用于处理不包含事件数据的事件。如果我们想用这种定义方式的同时,还使事件包含事件数据,那我们可以通过派生EventArgs类来实现。

//自定义事件,并使其带有事件数据
public class WaterEventHandler:EventArgs
{
    public string Message;
    public WaterEventHandler(string msg)
    {
        Message=msg;
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/83769.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

计算机研究生就业方向之考编

我一直跟学生们说你考计算机的研究生之前一定要想好你想干什么,如果你只是转码,那么你不一定要考研,至少以下几个职位研究生是没有啥优势的: 1,软件测试工程师(培训一下就行) 2,前…

MyBatis的缓存机制

文章目录1 MyBatis的一级缓存1.1 演示1.2 使一级缓存失效的四种情况2 MyBatis的二级缓存2.1 演示2.2 使二级缓存失效的情况:2.3 二级缓存的相关配置(了解即可)3 MyBatis缓存查询的顺序1 MyBatis的一级缓存 一级缓存是SqlSession级别的&#…

【vue加载16秒优化到2秒】Vue3加载慢的性能优化,打包后页面静态资源chunk-vendors文件过大加载慢响应慢

【写在前面】基于自己之前做vue3项目的时候发现了一个致命的问题,项目部署好了,但是加载起来反应慢半天,控制台一看才发现,有个chunk-vendors的js文件加载了十几秒,这无非是页面体验差到爆炸。今天就针对打包后静态资源…

【密码学基础】混淆电路(Garbled Circuit)

1 概念 混淆电路是一种密码学协议,以实现安全多方计算(MPC)。场景是当多个通信方需要共同输入数据,然后通过同一个函数计算出一个结果,但是,各个通信方都不允许其他人知道自己的输入是什么。混淆电路就能很…

MySQL错误码大全

MySQL的所有错误码可以从MySQL官网查看。 1.MySQL地址 首页网址 2.文档地址 以此点击如下标志。 MySQL8.0文档地址 3.错误码地址 服务码官网地址 点进去之后,可以看到: 分为三大类: Server Error Message ReferenceClient Error Mes…

Java大型建筑建设综合工程项目管理系统源码带原生APP源码 工程管理系统源码 Java手机端工程项目管理系统源码带客户端操作手册

客户端下载: 1、安卓手机端 先下载“PP助手”应用商店,再在PP助手中搜索“star工程”下载安装。 2、苹果手机端 苹果手机APPstore中搜索“star工程”下载安装。 建设综合工程项目管理系统,让公司业务管理实现可记录,可追踪&#…

数字图像处理(入门篇)七 图像数据预处理之灰度变化

目录 一 常用操作 1 反转 2 对比度增强 3 对比度压缩 4 伽马矫正 二 实践 1 反转、对比度增强和对比度压缩 (1) 代码 (2) 结果图 2 伽马矫正 (1) 代码 (2) 结果图 (3) 结论 (4) np.power函数 图像灰度变换:将原始图像中的每一个点的灰度值&#xff0c…

尚医通 (三十三) -------- 阿里云OSS、用户认证与就诊人

目录一、阿里云 oss1. 开通 对象存储 OSS 服务2. 使用 SDK 文档3. 文件服务实现搭建 service-oss 模块测试SDK封装 service 接口封装 controller 接口二、用户认证1. 需求分析2. api 接口3. 前端4. 预约挂号页面调整三、就诊人管理1. 需求分析2. api 接口3. 前端四、平台用户管…

最新阿里云服务器和GPU服务器长期优惠活动价格表

阿里云服务器优惠活动是长期的,在12月优惠活动大促期间云服务器价格会有所调整,主机教程网现在给大家分享最新的阿里云服务器优惠活动价格表。现在阿里云双十一优惠活动刚刚结束,随之而来的就是双12优惠活动,关于阿里云服务器、对…

camunda入门教程及实现原理

1、camunda简介 1、介绍: Camunda是一种工作流引擎。 Camunda BPM 是一个轻量级、开源灵活的工作流框架,是由Java开发的一个纯Java库。它的核心是一个在Java虚拟机内部运行的原生BPMN 2.0流程引擎,因此它可以嵌入到任何Java应用程序或运行时…

Linux 添加环境变量的两种方法 exprot 临时法 vi /etc/profile永久法

编写一个shell脚本之后,怎么可在任意目录运行改脚本呢?为什么别人写的脚本可以直接运行,自己写的脚本就会出现 -bash: XXXXX.sh: command not found 这样的错误呢? 1、举例验证,先新建一个HelloWorld的shell脚本&…

Alibaba 工具型技术系列,实战技术针对于项目中常用的 Excel 操作指南

ExcelIgnoreUnannotated 默认不加 ExcelProperty 的注解的都会参与读写,加了不会参与 通用参数 ReadWorkbook,ReadSheet 都会有的参数,如果为空,默认使用上级。 converter 转换器,默认加载了很多转换器。也可以自定义。 rea…

emlog模板开发基础2022最新指南

emlog模板的开发基础指南,如果想要开发emlog的模板,你必须知道那些开发内容呢?下面将介绍分析emlog5下的模板基本结构以及基本变量、函数的作用。 首先我们用该知道emlog的模板是位于根目录content\templates\文件夹下,每个模板都是一个单独的文件夹,文件夹以模板名…

[附源码]JAVA毕业设计-英杰学堂网上教学平台-(系统+LW)

[附源码]JAVA毕业设计-英杰学堂网上教学平台-(系统LW) 项目运行 环境项配置: Jdk1.8 Tomcat8.5 Mysql HBuilderX(Webstorm也行) Eclispe(IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持)。 项…

一道关于Vue的数据绑定和依赖收集的面试题

概要 分享一道Vue的面试题,该题涉及Vue的响应式数据绑定和依赖收集,希望可以加深大家对Vue原理的理解。 题面 有如下html和JS,要求使用Vue的响应式数据原理和依赖收集原理,实现createApps和ref方法。只能使用原生JS&#xff0c…

教育的本质——采用不同学习方式,学习者在两周后还能记住的内容有多少

目录 一、学习金字塔模型 二、学习曲线 三、左右脑交替学习法 一、学习金字塔模型 “学习金字塔模型”,人们学习的效率一共分为七个层次: 第一层 ~ 第四层:这是我们最熟悉不过的形式,在学生时代,老师在上面讲课、…

【Leetcode】225. 用队列实现栈、232. 用栈实现队列

作者:一个喜欢猫咪的的程序员 专栏:《Leetcode》 喜欢的话:世间因为少年的挺身而出,而更加瑰丽。 ——《人民日报》 目录 225. 用队列实现栈 232. 用栈实现队列 225. 用队列实现栈 225. 用队…

91-143-Scala-集合模式泛型等

91-Scala-集合模式泛型等: Scala 的集合有三大类:序列 Seq、集 Set、映射 Map,所有的集合都扩展自 Iterable特质。 2)对于几乎所有的集合类,Scala 都同时提供了可变和不可变的版本,分别位于以下两个包 不…

人工智能(AI)背后人工的力量——数据标注

尽管随着AI的普及,我们在生活中越来越依赖于人工智能,但“人工智障”的相关调侃也从来没有消失过。 相信大家都知道,如果我们想要让AI准确识别出图中的鸟,我们需要在数据集中手动将这些照片标记为鸟,然后让算法和图像…

c3p0数据库连接池的使用

c3p0数据库连接池的使用 c3p0的官网:c3p0 - JDBC3 c3p0数据库连接池有两种方法 导入jar包 首先两种方法都需要导入jar包 图中打钩的,第一个是c3p0的包,第二个是连接数据库的 在WEB-INF下新建lib包,将所需要的jar导入 右键添加…