趁着1024这个好日子来讲一下

通常在C# 中
为了将功能模块化
我们会把重复使用的功能写到类 (Class)里面
但是写在类里面的方法是无法直接对主窗体界面进行操作的
这个时候我们就需要使用 “委托”
关于委托的讲解可以参考这篇
https://www.cnblogs.com/wudiwushen/archive/2010/04/20/1703368.html
讲的挺浅显易懂的
但随着时代的进步
程式语言也在进步(人越来越懒)

现在我们只需要在类中声明一个Event Action的变量
就可以让随时呼叫并执行我们在主界面的方法
而主界面的方法就可以对界面进行操作拉

类class Class1{public event Action Call;  <--记得要用public才找得到public void Show(){Call.Invoke();}}
Form1public partial class Form1 : Form{Class1 c1;public Form1(){InitializeComponent();}private void Form1_Load(object sender, EventArgs e){c1 = new Class1();c1.Call += Called;  <---注意这里}private void Called(){label1.Text = "123";}private void button1_Click(object sender, EventArgs e){c1.Show();   <--会在Show里面invoke到Called}}

Form1中+=使用的就是一个委托的概念
意思是当c1 这个object(类的实例化)里面的Call (呼叫)这个Event Action的时候
会呼叫到Form1 (主界面)中的Called (被呼叫)方法


这个时候的顺序应该是

  1. 按下button1
  2. 执行c1.show()
  3. show方法中执行Call.Invoke()
  4. Call.Invoke()呼叫Called方法执行 (因为 c1.Call += Called这句)
  5. 执行Called方法
  6. 将Label1的文字修改为 “123”

那么若是
多了一个button里头执行

    private void button2_Click(object sender, EventArgs e){c1.Call -= Called;}

会发生什么事?

我们再理清一下顺序

  1. 按下button1
  2. 执行c1.show()
  3. show方法中执行Call.Invoke()
  4. Call.Invoke()呼叫Called方法执行 (因为 c1.Call += Called这句)
  5. 执行Called方法
  6. 将Label1的文字修改为 “123”
    --------到这边位置都一样--------
  7. 按下button2 (c1.Call -= Called 取消注册)
  8. 按下button1
  9. 执行c1.show()
  10. show方法中执行Call.Invoke()
  11. 因为Call并没有注册任何的方法,系统不知道要呼叫谁就报错了

那有没有方法避免呢? 是有的

  public void Show(){Call?.Invoke();}

看得出来差在哪里吗?
其实就只加了一个?上去而已
但这个问号在的功用等于

 if (Call != null) { Call.invoke();}

因为Call并未注册 (被取消注册) 所以没有任何值或地址在里面
所以便不会执行Call.Invoke()了

再来 如果我们要将变量透过invoke()传递该怎么做呢?
很简单

类public event Action<string> Call;  <--代表呼叫接收一个string的方法public void Show(){string text = "456";Call?.Invoke(text);}
Form1Class1 c1;public Form1(){InitializeComponent();}private void Form1_Load(object sender, EventArgs e){c1 = new Class1();c1.Call += Called;}private void Called(string text)  <--接收一个string{label1.Text = text;}private void button1_Click(object sender, EventArgs e){c1.Show();}private void button2_Click(object sender, EventArgs e){c1.Call -= Called;}

当然 你也可以不只传递一个参数

 public event Action<int, string, string> Call;public void Show(){int time = 2;string text1 = "456";string text2 = "789";Call?.Invoke(time, text1, text2);}
 Class1 c1;public Form1(){InitializeComponent();}private void Form1_Load(object sender, EventArgs e){c1 = new Class1();c1.Call += Called;}private void Called(int time, string text1, string text2){for(int i=0; i<time; i++){label1.Text += text1;label1.Text += text2;label1.Text += "x";}}private void button1_Click(object sender, EventArgs e){c1.Show();}private void button2_Click(object sender, EventArgs e){c1.Call -= Called;}

C# Event Action与Invoke相关推荐

  1. unity学习-委托(delegate),事件(event),Action,Func

    unity学习 委托 含义 定义 使用 事件 含义 使用 在进行项目的过程中,一直存在着对代码管理不当的问题,所以需要学习一些科学的代码思维,减少后期功能的修改与迭代引发的代码冗杂和内存爆炸 可以看b ...

  2. C# delegate、event、Action、Func使用案例解析

    C# 中 delegate.event.Action.Func使用案例解析 一:delegate与event配合使用 public static class Evt_Test{public stati ...

  3. 第十节:委托和事件(2)(泛型委托、Func和Action、事件及与委托的比较)

    一. 泛型委托 所谓的泛型委托,即自定义委托的参数可以用泛型约束,同时内置委托Func和Action本身就是泛型委托. 将上一个章节中的Calculator类中的方法用自定义泛型委托重新实现一下. 1 ...

  4. 【wpf】自定义事件总结(Action, EventHandler)

    Action和EventHandle Action和EventHandler都是.net帮我定义好的委托,我们可以直接使用,方便的定义事件. 利用Action定义事件 //无参事件 event Act ...

  5. mysql数据库什么是事件_MySQL数据库之mysql 事件(Event) 总结

    本文主要向大家介绍了MySQL数据库之mysql 事件(Event) 总结 ,通过具体的内容向大家展现,希望对大家学习MySQL数据库有所帮助. 1 事件简介 事件(event)是MySQL在相应的时 ...

  6. C#并行编程中的Parallel.Invoke

    一.基础知识 并行编程:并行编程是指软件开发的代码,它能在同一时间执行多个计算任务,提高执行效率和性能一种编程方式,属于多线程编程范畴.所以我们在设计过程中一般会将很多任务划分成若干个互相独立子任务, ...

  7. 语法之知识点的改进(Func/Action)

    上一章我们讲到关于面向对象思想上C#和JAVA之差别.笔者分别从面向对象的三大特性入手.而本章主要讲一些C#改进的知识点.在.NET Framework 2.0之后出现很多新的知识点.这些知识点更是让 ...

  8. 【Level 08】U06 Good Feeling L4 The surprising event

    文章目录 Word Preparation sadden: 使悲伤 heartwarming: 感人的 extraordinary story: 离奇的故事 must-read: 必读书目 quite ...

  9. 委托、Lambda表达式、事件系列06,使用Action实现观察者模式,体验委托和事件的区别...

    在"实现观察者模式(Observer Pattern)的2种方式"中,曾经通过接口的方式.委托与事件的方式实现过观察者模式.本篇体验使用Action实现此模式,并从中体验委托与事件 ...

  10. Event Sourcing和CQRS实现

    Event Sourcing和CQRS实现 文章参考自: https://github.com/soooban/AxonDemo 相关资料: https://blog.csdn.net/quguang ...

最新文章

  1. SyntaxError: Non-ASCII character ‘\xe4‘ in file xx(路径)
  2. 「屋漏偏逢连夜雨」,Log4j 漏洞还没忙完,新的又来了
  3. opencv python教程简书_OpenCV-Python系列二:常用的图像属性
  4. mockjs语法规范、设置mockjs拦截响应时间、Mock.Random占位符生成随机数据
  5. redis之事务主从复制
  6. rosdep init 和rosdep update的解决方法,亲测有效
  7. 狂打气球html5游戏_4399h5游戏_企业团建活动小游戏:合力吹气球
  8. 数据结构和算法(C语言版)期末速成基础不挂科补考
  9. JavaScript参考手册
  10. tkmybatis VS mybatisplus
  11. 五线谱音名和组别对照表_五线谱简谱对照表
  12. 关于2021年个人公众号总结
  13. Java的Exception异常机制(一)
  14. 小米下拉导航栏,36kr 下拉导航栏解决方法
  15. logstash 导入数据,查看每秒导入的数据量及已导入数量和已导入时间
  16. windows 下 redis服务经常自动关闭
  17. 支付宝花呗额度一直不涨?阿里老员工说出原因,亲测有效
  18. squeeze 、unsequeeze
  19. 传感器的使用,高仿微信摇一摇,动画加声音
  20. 2022图像翻译/扩散模型:UNIT-DDPM: UNpaired Image Translation with Denoising Diffusion Probabilistic Models

热门文章

  1. 从零开始的iOS开发:10 | 如何构建一个APP
  2. 小计一次监听器的报错之--ORA-12170
  3. 如何设计一个电商平台积分兑换系统!
  4. 网络安全笔记-99-渗透-业务安全
  5. 【工作记录】VRLe工作总结
  6. 一个屌丝程序猿的人生(二十二)
  7. 为什么1//0.1等于9.0,而1//-0.1=-10?
  8. 基于dotNET 5 MVC经典模式引入Swagger进行web api开发和管理发布OAS3标准接口文档全过程
  9. 使用nginx配置子域名
  10. JAVA多线程并发之线程实现,4种线程池,终止线程4种方式