How virtual events work in C#?(虚拟事件如何在 C# 中工作?)
问题描述
以下是我用于测试的程序.它打印(如预期):
Below is the program I used for the test. It prints (as expected):
Raise A
Event from A
Raise B
Event from B
现在,如果我们将 Main 的前两行更改为:
Now, if we change first two lines of the Main to be:
A a = new B();
B b = new B();
程序将打印:
Raise A
Raise B
Event from B
这也是意料之中的,因为覆盖事件隐藏了基类中的私有支持字段,因此基类触发的事件对派生类的客户端不可见.
which is also expected, as overriding event hides the private backing field in the base class and therefore events fired by the base class are not visible to clients of the derived class.
现在我将相同的行更改为:
Now I am changing the same lines to:
B b = new B();
A a = b;
程序开始打印:
Raise A
Raise B
Event from A
Event from B
发生了什么事?
class A
{
public virtual event EventHandler VirtualEvent;
public void RaiseA()
{
Console.WriteLine("Raise A");
if (VirtualEvent != null)
{
VirtualEvent(this, EventArgs.Empty);
}
}
}
class B : A
{
public override event EventHandler VirtualEvent;
public void RaiseB()
{
Console.WriteLine("Raise B");
if (VirtualEvent != null)
{
VirtualEvent(this, EventArgs.Empty);
}
}
}
class Program
{
static void Main(string[] args)
{
A a = new A();
B b = new B();
a.VirtualEvent += (s, e) => Console.WriteLine("Event from A");
b.VirtualEvent += (s, e) => Console.WriteLine("Event from B");
a.RaiseA();
b.RaiseB();
}
}
推荐答案
我们有一个(B的)实例,它具有以下字段:
We have a single instance (of B) which has the following fields:
- A.VirtualEvent: null
- B.VirtualEvent:两个事件处理程序
对 a.RaiseA()
的调用 只是 打印Raise A" - 仅此而已,因为 A 中的私有字段为空.
The call to a.RaiseA()
just prints "Raise A" - but nothing more, because the private field in A is null.
对 b.RaiseB()
的调用会打印剩余的三行,因为该事件已被订阅了两次(一次打印来自 A 的事件",一次打印来自 B 的事件").
The call to b.RaiseB()
prints the remaining three lines, because the event has been subscribed to twice (once to print "Event from A" and once to print "Event from B").
这有帮助吗?
为了更清楚 - 将虚拟事件视为一对虚拟方法.很像这样:
To make it clearer - think of the virtual event as a pair of virtual methods. It's very much like this:
public class A
{
private EventHandler handlerA;
public virtual void AddEventHandler(EventHandler handler)
{
handlerA += handler;
}
public virtual void RemoveEventHandler(EventHandler handler)
{
handlerA -= handler;
}
// RaiseA stuff
}
public class B : A
{
private EventHandler handlerB;
public override void AddEventHandler(EventHandler handler)
{
handlerB += handler;
}
public override void RemoveEventHandler(EventHandler handler)
{
handlerB -= handler;
}
// RaiseB stuff
}
现在更清楚了吗?这不是完全那样,因为据我所知,您不能只覆盖事件的部分"(即其中一种方法),但它给人的总体印象是正确的.
Now is it clearer? It's not quite like that because as far as I'm aware you can't override just "part" of an event (i.e. one of the methods) but it gives the right general impression.
这篇关于虚拟事件如何在 C# 中工作?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!
本文标题为:虚拟事件如何在 C# 中工作?
基础教程推荐
- 如何在 IDE 中获取 Xamarin Studio C# 输出? 2022-01-01
- SSE 浮点算术是否可重现? 2022-01-01
- MS Visual Studio .NET 的替代品 2022-01-01
- c# Math.Sqrt 实现 2022-01-01
- 将 Office 安装到 Windows 容器 (servercore:ltsc2019) 失败,错误代码为 17002 2022-01-01
- 有没有办法忽略 2GB 文件上传的 maxRequestLength 限制? 2022-01-01
- 为什么Flurl.Http DownloadFileAsync/Http客户端GetAsync需要 2022-09-30
- 如何激活MC67中的红灯 2022-01-01
- rabbitmq 的 REST API 2022-01-01
- 将 XML 转换为通用列表 2022-01-01