1、委托——delegate\Action

1.1 delegate

委托可以理解为函数指针。
委托delegate关键词,Delegate和delegate都可以,这个类似于string和String,c#程序编写一般还是用delegate小写的。委托定义的变量和类定义的变量一样,也是一种类型的对象。

public delegate void Game();//定义一个委托,这是一个类型,注意区别类型和对象的区别,对象是类型的具体化可以这样理解,Game现在就是一个类型,可以用Game定义Game类型的对象,这个类型是无返回值无参数的委托类型
//声明一种委托对象的方式
//方式01
public Game game_01;//定义一个委托的实例对象,和定义变量一样,直接定义,这时候game_01值为null
//方式02
Game game_01=new Game(“方法名称”);//和类的声明不同,委托声明的时候括号内必须有值,也就是方法名称,错误提示为“Game不包含0个参数的构造函数”,类括号内无参数是因为类的构造函数没有参数public void Play(Game game)
{//委托的执行方式有
//方式01,直接加上括号,就执行了所指向的方法
game();
//方式02,
game.Invoke();//这种方式也有人在用,一般都是用上一种方法,这一种见到了知道是什么意思就行
}
//下面定义了几个游戏
public void WangZheRongYao()
{Console.WriteLine("王者荣耀");
}
public void HePingJingYing()
{Console.WriteLine("和平精英");
}static void Main(string[] args){Game game;game=WangZheRongYao;Play(game);//Play需要传入的是委托类型Console.ReadKey();#regionGame game_01=new Game(WangZheRongYao);Play(game_01);Console.ReadKey();#endregion}

可以这样理解:delegate这个关键词的使用和class关键词的使用类似。首先是这两个关键词在写法上是小写,其次在创建上也是非常相近,还有就是委托和类的等级一样,都是定义在命名空间,委托不是包含在类中,当然委托也可以定义在类中,委托类型是一种函数指针,就是等于函数名称,这个委托类型的变量保存的就是这个函数在内存中的地址。
另外在声明委托对象和类对象的时候有点不同,用new关键字后面的括号里面委托需要传入参数,类因为有无参的构造函数所以不要传入参数。

  1. 委托是引用类型,在没有被赋值时候为null;
  2. 因为委托存放的为函数地址,所以定义委托时候会有“返回值类型”和“括号”以及“括号内的形参”;
  3. 理解声明和定义,在创建类的时候总是说“定义一个类”,定义一个新的委托类型的时候会说“声明委托”
  4. 委托声明了以后就定了可以由这个委托引用的方法,这个委托就只能引用和他有相同标签的方法,也就是说和他有相同返回值和传入参数的方法;
  5. 一旦声明了委托类型,委托对象要用new关键字来创建,且与一个方法有关;
  6. 一旦声明了一个或者说定义了一个类对象,类对象就要用new关键字来创建,并调用构造函数,
  7. 其实类和委托一样
  8. 需要注意的是:委托对象创建的时候new关键字后面括号里面为函数名称,不带参数;

例如:

//我们在定义一种新“对象”类型的时候
//定义一个学生Student类
public class Student
{}
//实例化一个student对象
Student student=new Student();//无参数,调用的是构造函数
//我们在定义一个新的委托类型的时候
//定义一个新“委托”类型的时候
//定义一个Delegate委托
public delegate void DD();
DD dd=new DD(function);//有参数,参数为function,必须有参数,因为委托没有构造方法
dd();//这就算执行了function函数了,就是在委托变量的后面加上括号,也可以dd.Invoke()

1.2 Action

    class Interpreter{public void SayHi(Action language){language.Invoke();}public void Chinese(){Console.WriteLine("你好");}}static void Main(string[] args){Interpreter interpreter = new Interpreter();Action language = interpreter.Chinese;interpreter.SayHi(language);Console.ReadKey();}
    public delegate void Language();//定义一个委托类型class Interpreter{public void SayHi(Language language){//language();language.Invoke();}public void Chinese(){Console.WriteLine("你好");}}static void Main(string[] args){Language language;Interpreter interpreter = new Interpreter();//下面的这个动作就可以理解为插卡动作language = interpreter.Chinese;//注意这里不能加括号,只是把函数名的地址给到委托if(language==null){Console.WriteLine("没有检测的插卡!");}interpreter.SayHi(language);Console.ReadKey();}

从上面两段代码可以看出来,Action就是委托,只是对delegate的进一步封装,用action就不用先定义委托了。

2、线程——Thread/Task

线程=任务
Task是Thread的一个包装类,使用方法基本上和Thread一样

ParameterizedThreadStart ParStart = new ParameterizedThreadStart(ThreadMethod);Thread myThread = new Thread(ParStart);object o = "hello";myThread.Start(o);//ThreadMethod如下:public void ThreadMethod(object ParObject){//程序代码}

带参数的方法需要这样开多线程

Thread线程
Task任务,对线程的封装
Task.Run();
delegate委托
event delegate
Action对委托的封装
event Action()
时间委托
委托的广播和订阅,实现数据传递
this.Invoke(new Action(()=>{});委托给一个匿名函数
线程的取消
CancellationTokenSource

2.1 同步

同步的sync,界面会卡顿,

2.2 多线程

开启多个线程,多个线程会同时执行

2.3 异步多线程

异步多线程是像同步一样,执行上有一定的顺序,异步多线程有关键字await、async关键字

3、事件——event

关于委托事件event和多线程Thread,这两个会一起出现,这是一种设计模式的问题,委托事件的广播和订阅的概念,
如果一个进程中有多个线程,线程之间的数据是不能被调用和访问的,一个线程想要访问其他线程的数据就要用的委托,用到委托就有了委托事件,就有了委托事件的广播和订阅的概念。
委托事件的定义和委托一样,就是在关键词Action前面加上event关键字
委托事件的订阅是“+=”,vs可以自动生成订阅事件的函数

class TaoBao//定义了一个淘宝类型,
{List<string> list =new List<string>
{"淘宝产品-01",
"淘宝产品-02",
"淘宝产品-03",
"淘宝产品-04",
"淘宝产品-05",
"淘宝产品-06",
"淘宝产品-07",
"淘宝产品-08",
"淘宝产品-09",
"淘宝产品-10",
}
public event Action<string> SetDatas;//这里定义了一个委托事件,函数名为SetDatas,带参数,参数为string类型//其他方法
public void CollectDatas()
{foreach(string item in list)//list是一个列表数据,这里是取出每个元素{SetDatas(item);//把采集到的数据通过一个委托方法发送到别的线程,这里是主窗体的UI线程,//调用这个方法就是把数据广播出去,谁订阅就能得到这个数据,进而处理这个数据Thread.Sleep(1000);
}
}
//这里写订阅
private void btnStart_Click(object sender,EventArgs e)
{//实例化一个淘宝类TaoBao taobao =new TaoBao();taobao.SetDatas+=Taobao_SetDatas;//这里就是订阅事件,这里vs可以自动给你定义一个委托方法,方法的名称//方法的名称和定义都自动可以生成,这里只是订阅了事件,但是现在这个实例化对象还是空值null,里面并没有数据Thread t1=new Thread(taobao.CollectDatas);//创建一个线程,传入的参数是一个委托类型,也就是一个函数名称t1.Start();//开启线程任务}
private void Taobao_SetDatas(string obj)
{//上面的obj就是广播过来的字符串string格式的数据,现在通过订阅到这个广播,就能拿到这个数据
//拿到这个数据后就可以把它赋值给窗体上的控件,
this.lbDatas.Invoke(new Action(()=>{//关于句柄,窗体上的控件都有一个句柄id作为标识,这里就是找到这个控件所在的
//线程,让后把数据给到这个线程,然后显示的
//注意:其实这里执行的代码是窗体线程的,this.lbDatas.Items.Add(obj);
}));
}

4、lamda表达式

运算符 “=>”意思是:go to
(参数)=>{函数体}
意思是参数传递到函数体内,可以这样的理解。

C#学习笔记之——委托、线程、事件、lamda表达式相关推荐

  1. [读书笔记]C#学习笔记二: 委托和事件的用法及不同.

    前言:  C#委托是什么 c#中的委托可以理解为函数的一个包装, 它使得C#中的函数可以作为参数来被传递, 这在作用上相当于C++中的函数指针. C++用函数指针获取函数的入口地址, 然后通过这个指针 ...

  2. Windows事件等待学习笔记(四)—— 事件信号量互斥体

    Windows事件等待学习笔记(四)-- 事件&信号量&互斥体 要点回顾 事件 实验:验证SignalState 第一步:编译并运行以下代码 第二步:观察结果 第三步:修改代码并执行 ...

  3. JavaScript学习笔记(三)---事件、正则表达式、ES6、运动

    JavaScript学习笔记(三)---事件.正则表达式.ES6.运动 27.insertbefore 28.滚动条及事件 29.事件及事件对象 30.鼠标事件对象的属性 31.案例:图片随鼠标移动 ...

  4. Java学习笔记:创建线程的两种方法

    Java学习笔记:创建线程的两种方法 一.预备工作 1.创建Maven项目ThreadDemo 2.在pom.xml里添加依赖 二.继承Thread类创建子线程

  5. Mcad学习笔记之委托再理解(delegate的构造器,MulticastDelegate,BeginInvoke,EndInvoke,Invoke4个方法的探讨)...

    相关文章导航 Sql Server2005 Transact-SQL 新兵器学习总结之-总结 Flex,Fms3相关文章索引 FlexAir开源版-全球免费多人视频聊天室,免费网络远程多人视频会议系统 ...

  6. oracle job enq tx,【学习笔记】Oracle等待事件 enq:TX–allocate ITL entry产生原因和解决办法...

    天萃荷净 运维DBA反映Oracle数据库出现enq:TX–allocate ITL entry等待事件,结合案例分析该等待事件产生原因和解决办法 今天在分析一份awr中发现了较为明显的enq: TX ...

  7. C++ Primer 学习笔记(第四章:表达式)

    2019独角兽企业重金招聘Python工程师标准>>> ##C++ Primer 学习笔记(第四章:表达式) [TOC] ###4.1 基础 左值和右值: 当一个对象被用作右值的时候 ...

  8. Java快速入门学习笔记3 | Java语言中的表达式与操作符

    有人相爱,有人夜里开车看海,有人却连LeetCode第一题都解不出来!虽然之前系统地学习过java课程,但是到现在一年多没有碰过Java的代码,遇到LeetCode不知是喜是悲,思来想去,然后清空自己 ...

  9. C++ 学习笔记(19)new/delete表达式、定位new、typeid、dynamic_cast、type_info、枚举类型、成员函数指针、union、位域、volatile限定符、链接指示

    C++ 学习笔记(19)new/delete表达式.定位new.typeid.dynamic_cast.type_info.枚举类型.成员函数指针.union.位域.volatile限定符.链接指示 ...

  10. C++ 学习笔记之(19) new、delete表达式、RTTI(运行时类型识别)、枚举、类成员指针、嵌套类、局部类、位域、volatile、extern C

    C++ 学习笔记之(19) new.delete表达式.RTTI(运行时类型识别).枚举.类成员指针.嵌套类.局部类.位域.volatile.extern C C++ 学习笔记之(19) new.de ...

最新文章

  1. 以高效节能为使命 绿色数据中心势在必行
  2. [css] 如何使用CSS的多列布局?
  3. leetcode 只出现一次的数字
  4. 从源码分析RocketMQ系列-Producer的SendResult的封装
  5. 42.从非托管磁盘创建虚拟机
  6. 冒泡排序的C语言实现
  7. html静态网页设计实训总结,网页设计实训心得体会范文
  8. LaTeX写数学公式
  9. 027 多分支选择结构
  10. C++ 侯捷视频学习(草稿)
  11. 高德地图加载标注并实现缩放动画
  12. HLS 3 FPGA并行化 稀疏矩阵向量乘法(计算机视觉)
  13. Arduino入门小知识点总结(2)(红外感应开关 与 继电器接法 模拟输入输出tone函数)
  14. 官方大大的的邮寄快递到啦
  15. speedoffice(Excel)表格中如何插入百分比符号
  16. nbu Linux 邮件告警,Netbackup配置邮件警报
  17. 4 win10环境下+vs2017+pcl1.9环境配置
  18. 谷歌浏览器驱动器下载网址
  19. 如何使用 OpenShift Container Platform 的命令行工具 OC
  20. UE4 后期处理体积 (角色受到伤害场景颜色变淡案例)

热门文章

  1. php $_get取得空,Laravel - PHP 無法取得 Hppt Request $_GET Params 值的解決方式
  2. 没有硬件,不押注AI,苹果在求稳中彻底quot;软quot;了
  3. java项目转成exe格式
  4. php读取文件名称,PHP获取文件名称的方法
  5. 扫码点餐成为餐厅的主流方式,你知道多少?
  6. 最新的关于计算机的设计方案,计算机毕业设计方案.doc
  7. Oracle - 5.0 - 【学习笔记】for ocp 12c、多租户(CDB、PDB)
  8. 如何在UDP的基础上设计可靠的链接
  9. 快速多人游戏(4) - 爆头!(AKA延迟补偿)
  10. Spring Boot 配置Kaptcha(谷歌验证码工具)(生成验证码、验证验证码)