2

在这段代码片段中,new MyDel(this.WelcomeUser)是如何工作的?内存中发生了什么,我知道委托是引用类型,那么在堆中是否创建了一个对象,它是哪种类型的对象 - MyDelthis.WelcomeUser到底是什么?它是对方法的引用吗?

using System;
namespace SampleApp {
public delegate string MyDel(string str);

class EventProgram {
  event MyDel MyEvent;

  public EventProgram() {
     this.MyEvent += new MyDel(this.WelcomeUser);
  }
  public string WelcomeUser(string username) {
     return "Welcome " + username;
  }
  static void Main(string[] args) {
     EventProgram obj1 = new EventProgram();
     string result = obj1.MyEvent("Tutorials Point");
     Console.WriteLine(result);
  }
 }
}
4

2 回答 2

4

怎么new MyDel(this.WelcomeUser)工作?

它是对构造函数的调用,this.WelcomeUser作为参数。

public delegate string MyDel(string str);

是一个类型定义。编译器使用它来生成一个派生自System.Delegate. 请注意,这是在 C# 有泛型之前设计的。

这到底是什么。欢迎用户?

它是一种方法的名称。在 C#(和 C、C++ 等)中,方法总是后跟参数(或参数)列表,即使该列表为空:SomeMethod().
省略列表相当于地址。

当您查看 VB.NET 时会变得更清楚,等效代码是

MyEvent += new MyDel(this.WelcomeUser);       // C#

AddHandler MyEvent, AddressOf Me.WelcomeUser  ' VB

从 C# 2 开始,您可以使用简写法:

MyEvent += this.WelcomeUser;       // modern C#
于 2019-08-01T07:06:26.440 回答
1

它是对函数的引用吗?

是的,但我们通常在 C# 中称它们为方法

  • this指当前类
  • WelcomeUser指类中的方法名。

new MyDel调用需要提供一个方法的名称,该方法接受一个字符串参数并返回一个字符串(即与 的输入和输出相匹配的东西delegate)。任何遵守这一点的方法都是可以接受的

在此处输入图像描述

看一个事件引发者和消费者属于不同类的例子可能更有意义:

using System;

public delegate string MyDel(string str);

class EventEmitter {
  event MyDel MyEvent;
}

class EventConsumer{

  private EventEmitter x = new EventEmitter();

  public EventConsumer() {
     x.MyEvent += new MyDel(this.MyEventHandler);
  }

  public string MyEventHandler(string username) {
     return "Welcome " + username;
  }

}

在这里,EventConsumer 现在可以知道 EventEmitter 何时引发了它的事件。EventEmitter 不知道使用者内部的任何方法、它们的名称等。.NET 运行时将调用附加到发射器中事件的方法(在使用者中)。可以附加多个处理程序:

class EventConsumer{

  private EventEmitter x = new EventEmitter();

  public EventConsumer() {
     x.MyEvent += new MyDel(this.MyEventHandler);
     x.MyEvent += new MyDel(this.MyEventHandler2);
  }

  public string MyEventHandler(string username) {
     return "Welcome " + username;
  }
  public string MyEventHandler2(string username) {
     return "Goodbye " + username;
  }

}

引发事件时,它们都将被调用(但不能保证以什么顺序) ..

事件机制很重要,因为它允许我们提供一种方法来提醒其他类发生了事情,而无需了解该类的任何信息。明显的用途类似于 Button 类 - Microsoft 不知道在编写 Button 时会调用您处理按钮单击的方法,因此他们只提供了一个名为 Click 的事件,并且您附加任何具有兼容签名的方法来处理用户按下按钮时的点击

于 2019-08-01T07:00:26.027 回答