namespace DelegateExample
{class Program{static void main(string[] args){Calculator calculator=new Calculator();//Action委托Action Cal=new Action(calculator.Report);//直接调用函数Calculator.Report();//通过委托调用函数Cal.Invoke();//简便写法Cal();//Func委托int a=100,b=200,c=0;Func func1=new Func(Calculator.Add); //尖括号中为<参数1,参数2,返回值>Func func2=new Func(Calculator.Sub);//利用委托调用函数c=func1.Invoke(a,b);//简便写法 c=func1(a,b)Console.WriteLine(c);c=func2.Invoke(a,b);//简便写法 c=func1(a,b)Console.WriteLine(c);}}class Calculator{public void Report(){console.WriteLine("123");}public int Add(int a,int b){int result=a+b;return result;}public int Sub(int a,int b){int result=a-b;return result;}}}
避免写错地方结果声明成嵌套类型:
一般委托的声明在命名空间内,和Program类同级,如果声明在Program类中,会声明成为嵌套类 类型。
namespace DelegateExample
{//自定义委托声明格式public delegate double Cal(double x,double y);class Program{static void main(string[] args){Calculator calculator=new Calculator();Cal cal1=new Cal(calculator.Add);Cal cal2=new Cal(calculator.Sub);Cal cal3=new Cal(calculator.Mul);Cal cal4=new Cal(calculator.Div);double a=200,b=100,c=0;c=cal1.invoke(a,b);Console.WriteLine(c);c=cal2.invoke(a,b);Console.WriteLine(c);c=cal3.invoke(a,b);Console.WriteLine(c);c=cal4.invoke(a,b);Console.WriteLine(c);} }class Calculator{public double Add(double a,double b){return a+b;}public double Sub(double a,double b){return a-b;}public double Mul(double a,double b){return a*b;}public double Div(double a,double b){return a/b;}}}
using System;
using System.Collections.Generic;namespace DelegateExample
{class Program{static void Main(string[] args){WrapFactory wrapFactory = new WrapFactory();ProductFactory productFactory = new ProductFactory();Func func1 = new Func(productFactory.MakePizza);Func func2 = new Func(productFactory.MakeToyCar);Box box1 = wrapFactory.WrapProduct(func1);Box box2 = wrapFactory.WrapProduct(func2);Console.WriteLine(box1.Product.Name);Console.WriteLine(box2.Product.Name);Console.ReadKey();}}class Product{public string Name{ get; set; }}class Box{public Product Product { get; set; }}class WrapFactory{public Box WrapProduct(Func getProduct){Product product = getProduct.Invoke();Box box = new Box();box.Product = product;return box;}}class ProductFactory{public Product MakePizza(){Product product = new Product();product.Name = "Pizza";return product;}public Product MakeToyCar(){Product product = new Product();product.Name = "Toy Car";return product;}}}
//使用模板方法的好处,代码复用性高,只需要扩充ProductFactory类中的方法
//Product类、WrapFactory类,均不用修改
需求:
使用委托的回调方法,在上述代码中实现,若产品价格大于等于50时,打印输出商品信息
using System;
using System.Collections.Generic;namespace DelegateExample
{class Program{static void Main(string[] args){WrapFactory wrapFactory = new WrapFactory();ProductFactory productFactory = new ProductFactory();Func func1 = new Func(productFactory.MakePizza);Func func2 = new Func(productFactory.MakeToyCar);Logger logger = new Logger();Action log = new Action(logger.Log);Box box1 = wrapFactory.WrapProduct(func1,log);Box box2 = wrapFactory.WrapProduct(func2,log);Console.WriteLine(box1.Product.Name);Console.WriteLine(box2.Product.Name);Console.ReadKey();}}class Logger{public void Log(Product product){Console.WriteLine("Product '{0}' created at {1}. Price is {2}.", product.Name, DateTime.UtcNow, product.Price);}}class Product{public string Name{ get; set; }public double Price { get; set; }}class Box{public Product Product { get; set; }}class WrapFactory{public Box WrapProduct(Func getProduct,Action logCallback){Product product = getProduct.Invoke();if (product.Price >= 50){logCallback(product);}Box box = new Box();box.Product = product;return box;}}class ProductFactory{public Product MakePizza(){Product product = new Product();product.Name = "Pizza";product.Price = 20;return product;}public Product MakeToyCar(){Product product = new Product();product.Name = "Toy Car";product.Price = 99;return product;}}}
using System;
using System.Collections.Generic;
using System.Threading;
namespace DelegateExample
{class Program{static void Main(string[] args){Student stu1 = new Student() { ID = 1, PenColor = ConsoleColor.Yellow };Student stu2 = new Student() { ID = 1, PenColor = ConsoleColor.Green };Student stu3 = new Student() { ID = 1, PenColor = ConsoleColor.Red };Action action1 = new Action(stu1.DoHomeWork);Action action2 = new Action(stu2.DoHomeWork);Action action3= new Action(stu3.DoHomeWork);//单播委托/*action1.Invoke();action2.Invoke();action3.Invoke();*///多播委托action1 += action2;action1 += action3;action1.Invoke();Console.ReadKey();}}class Student{public int ID { get; set; }public ConsoleColor PenColor { get; set; }public void DoHomeWork(){for (int i = 0; i < 5; i++){Console.ForegroundColor = this.PenColor;Console.WriteLine("Student {0} doing homework {1} hour(s).", this.ID, i);Thread.Sleep(1000);}}}}
首先了解一下同步调用
直接同步调用与间接同步调用
using System;
using System.Collections.Generic;
using System.Threading;
namespace DelegateExample
{class Program{static void Main(string[] args){Student stu1 = new Student() { ID = 1, PenColor = ConsoleColor.Yellow };Student stu2 = new Student() { ID = 1, PenColor = ConsoleColor.Green };Student stu3 = new Student() { ID = 1, PenColor = ConsoleColor.Red };//直接同步调用/*stu1.DoHomeWork();stu2.DoHomeWork();stu3.DoHomeWork();*///间接同步调用Action action1 = new Action(stu1.DoHomeWork);Action action2 = new Action(stu2.DoHomeWork);Action action3 = new Action(stu3.DoHomeWork);action1.Invoke();action2.Invoke();action3.Invoke();//或者使用多播委托,也是同步调用的//action1+=action2;action1+=action3;action1.Invoke();for (int i = 0; i < 10; i++){Console.ForegroundColor = ConsoleColor.Cyan;Console.WriteLine("Main thread {0}.", i);Thread.Sleep(1000);}Console.ReadKey();}}class Student{public int ID { get; set; }public ConsoleColor PenColor { get; set; }public void DoHomeWork(){for (int i = 0; i < 5; i++){Console.ForegroundColor = this.PenColor;Console.WriteLine("Student {0} doing homework {1} hour(s).", this.ID, i);Thread.Sleep(1000);}}}
}
隐式异步调用
using System;
using System.Collections.Generic;
using System.Threading;
namespace DelegateExample
{class Program{static void Main(string[] args){Student stu1 = new Student() { ID = 1, PenColor = ConsoleColor.Yellow };Student stu2 = new Student() { ID = 1, PenColor = ConsoleColor.Green };Student stu3 = new Student() { ID = 1, PenColor = ConsoleColor.Red };//隐式异步调用Action action1 = new Action(stu1.DoHomeWork);Action action2 = new Action(stu2.DoHomeWork);Action action3 = new Action(stu3.DoHomeWork);action1.BeginInvoke(null,null);action2.BeginInvoke(null, null);action3.BeginInvoke(null, null);for (int i = 0; i < 10; i++){Console.ForegroundColor = ConsoleColor.Cyan;Console.WriteLine("Main thread {0}.", i);Thread.Sleep(1000);}Console.ReadKey();}}class Student{public int ID { get; set; }public ConsoleColor PenColor { get; set; }public void DoHomeWork(){for (int i = 0; i < 5; i++){Console.ForegroundColor = this.PenColor;Console.WriteLine("Student {0} doing homework {1} hour(s).", this.ID, i);Thread.Sleep(1000);}}}}
显式异步调用(古老的方式:使用Thread进行显示异步调用)
using System;
using System.Collections.Generic;
using System.Threading;
namespace DelegateExample
{class Program{static void Main(string[] args){Student stu1 = new Student() { ID = 1, PenColor = ConsoleColor.Yellow };Student stu2 = new Student() { ID = 1, PenColor = ConsoleColor.Green };Student stu3 = new Student() { ID = 1, PenColor = ConsoleColor.Red };/* Action action1 = new Action(stu1.DoHomeWork);Action action2 = new Action(stu2.DoHomeWork);Action action3 = new Action(stu3.DoHomeWork);//隐式异步调用action1.BeginInvoke(null,null);action2.BeginInvoke(null, null);action3.BeginInvoke(null, null);*///使用Thread进行显式异步调用Thread thread1 = new Thread(new ThreadStart(stu1.DoHomeWork));Thread thread2 = new Thread(new ThreadStart(stu2.DoHomeWork));Thread thread3 = new Thread(new ThreadStart(stu3.DoHomeWork));thread1.Start();thread2.Start();thread3.Start();for (int i = 0; i < 10; i++){Console.ForegroundColor = ConsoleColor.Cyan;Console.WriteLine("Main thread {0}.", i);Thread.Sleep(1000);}Console.ReadKey();}}class Student{public int ID { get; set; }public ConsoleColor PenColor { get; set; }public void DoHomeWork(){for (int i = 0; i < 5; i++){Console.ForegroundColor = this.PenColor;Console.WriteLine("Student {0} doing homework {1} hour(s).", this.ID, i);Thread.Sleep(1000);}}}
}
显式异步调用更高级的方式:Task,需要引用System.Threading.Tasks命名空间
using System;
using System.Collections.Generic;
using System.Threading;
using System.Threading.Tasks;
namespace DelegateExample
{class Program{public static object TTask { get; private set; }static void Main(string[] args){Student stu1 = new Student() { ID = 1, PenColor = ConsoleColor.Yellow };Student stu2 = new Student() { ID = 1, PenColor = ConsoleColor.Green };Student stu3 = new Student() { ID = 1, PenColor = ConsoleColor.Red };/* Action action1 = new Action(stu1.DoHomeWork);Action action2 = new Action(stu2.DoHomeWork);Action action3 = new Action(stu3.DoHomeWork);//隐式异步调用action1.BeginInvoke(null,null);action2.BeginInvoke(null, null);action3.BeginInvoke(null, null);*///使用Thread进行显式异步调用/*Thread thread1 = new Thread(new ThreadStart(stu1.DoHomeWork));Thread thread2 = new Thread(new ThreadStart(stu2.DoHomeWork));Thread thread3 = new Thread(new ThreadStart(stu3.DoHomeWork));thread1.Start();thread2.Start();thread3.Start();*///更高级的方式,使用Task进行显式异步调用Task task1 = new Task(new Action(stu1.DoHomeWork));Task task2 = new Task(new Action(stu2.DoHomeWork));Task task3 = new Task(new Action(stu3.DoHomeWork));task1.Start();task2.Start();task3.Start();for (int i = 0; i < 10; i++){Console.ForegroundColor = ConsoleColor.Cyan;Console.WriteLine("Main thread {0}.", i);Thread.Sleep(1000);}Console.ReadKey();}}class Student{public int ID { get; set; }public ConsoleColor PenColor { get; set; }public void DoHomeWork(){for (int i = 0; i < 5; i++){Console.ForegroundColor = this.PenColor;Console.WriteLine("Student {0} doing homework {1} hour(s).", this.ID, i);Thread.Sleep(1000);}}}
}
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Mhj2pXf5-1670512875811)(C:\Users\Wu\AppData\Roaming\Typora\typora-user-images\image-20221208185431055.png)]
用接口代替第一个案例中的委托
using System;
using System.Collections.Generic;namespace DelegateExample
{class Program{static void Main(string[] args){IProductFactory pizzaFactory = new PizzaFactory();IProductFactory toyCarFactory = new ToyCarFactory();WrapFactory wrapFactory = new WrapFactory();Box box1 = wrapFactory.WrapProduct(pizzaFactory);Box box2 = wrapFactory.WrapProduct(toyCarFactory);Console.WriteLine(box1.Product.Name);Console.WriteLine(box2.Product.Name);Console.ReadKey();}}interface IProductFactory{Product Make();}class PizzaFactory : IProductFactory{public Product Make(){Product product = new Product();product.Name = "Pizza";return product;}}class ToyCarFactory : IProductFactory{public Product Make(){Product product = new Product();product.Name = "Toy Car";return product;}}class Product{public string Name { get; set; }public double Price { get; set; }}class Box{public Product Product { get; set; }}class WrapFactory{public Box WrapProduct(IProductFactory productFactory){Product product = productFactory.Make();Box box = new Box();box.Product = product;return box;}}
}
1.初步了解
统一称为事件的订阅者
统一称为事件参数
2.动手操作
1.事件的简单示例
using System;
using System.Timers;
namespace EventExample
{class Program{static void Main(string[] args){Timer timer = new Timer();//timer为事件的拥有者timer.Interval = 1000;Boy boy = new Boy();//boy为事件的订阅者Girl girl = new Girl();timer.Elapsed += boy.Action;timer.Elapsed += girl.Action;timer.Start();Console.ReadLine();}}class Boy{internal void Action(object sender, ElapsedEventArgs e){Console.WriteLine("Jump!");}}class Girl{internal void Action(object sender, ElapsedEventArgs e){Console.WriteLine("Sing!");}}}
using System;
using System.Windows.Forms;namespace EventExample
{class Program{static void Main(string[] args){Form form = new Form();//form是事件的拥有者Controller controller = new Controller(form);//controller是事件的订阅者form.ShowDialog();}}class Controller{private Form form;public Controller(Form form){if (form != null){this.form = form;this.form.Click += this.FormClicked;//form.Click是事件成员,FromClicked是事件处理器}}private void FormClicked(object sender, EventArgs e){this.form.Text = DateTime.Now.ToString();}}
}
3.示例3
using System;
using System.Windows.Forms;namespace EventExample
{class Program{static void Main(string[] args){MyForm form = new MyForm();//form事件拥有者form.Click += form.FormClicked;//事件成员form.Click;事件处理器form.FormClicked;//事件订阅者也是form;form.ShowDialog();}}class MyForm : Form{internal void FormClicked(object sender, EventArgs e){this.Text = DateTime.Now.ToString();}}
}
4.示例4
using System;
using System.Windows.Forms;namespace EventExample
{class Program{static void Main(string[] args){MyForm form = new MyForm();form.ShowDialog();}}class MyForm : Form{private TextBox textBox;private Button button;//事件拥有者是实例化的 Form.buttonpublic MyForm(){this.textBox = new TextBox();this.button = new Button();this.Controls.Add(this.button);this.Controls.Add(this.textBox);this.button.Click += ButtonClicked;//button.Click是事件成员,//ButtonClicked是事件处理器//事件订阅者是MyForm的实例}private void ButtonClicked(object sender, EventArgs e){this.textBox.Text = "Hello, World!";}}
}
上一篇:TH9-搭建后台系统
下一篇:基于短时傅里叶函数的语谱图显示