gpt4 book ai didi

c# - 使用静态类/事件作为应用程序消息总线是否存在缺陷

转载 作者:太空狗 更新时间:2023-10-30 01:27:25 26 4
gpt4 key购买 nike

我有一个静态泛型类,它可以帮助我以很少的开销移动事件:

public static class MessageBus<T> where T : EventArgs
{
public static event EventHandler<T> MessageReceived;
public static void SendMessage(object sender, T message)
{
if (MessageReceived != null)
MessageReceived(sender, message);
}
}

要创建系统范围的消息总线,我只需定义一个 EventArgs 类来传递任意位的信息:

class MyEventArgs : EventArgs
{
public string Message { get; set; }
}

任何我对这个事件感兴趣的地方,我只需连接一个处理程序:

MessageBus<MyEventArgs>.MessageReceived += (s,e) => DoSomething();

同样,触发事件也同样简单:

MessageBus<MyEventArgs>.SendMessage(this, new MyEventArgs() {Message="hi mom"});

使用 MessageBus 和自定义 EventArgs 类让我拥有一个用于特定类型消息的应用程序范围的消息接收器。当您有多个表单时,这会派上用场,例如,显示客户信息以及更新该信息的几个表单。没有一种形式相互了解,也不需要连接到静态“父类(super class)”。

我有几个问题:

  1. fxCop 提示将静态方法与泛型一起使用,但这正是我在这里所追求的。我希望每种处理的消息类型都有一个 MessageBus。将 static 与泛型结合使用使我无需编写维护 MessageBus 对象列表的所有代码。

  2. 监听对象是否通过 MessageReceived 事件保持“事件”状态?

例如,也许我在 Form.Load 事件中有这段代码:

MessageBus<CustomerChangedEventArgs>.MessageReceived += (s,e) => DoReload();

当窗体关闭时,窗体是否保留在内存中,因为 MessageReceived 引用了它的 DoReload 方法?我是否应该在表单关闭时删除引用:

MessageBus<CustomerChangedEventArgs>.MessageReceived -= (s,e) => DoReload();

最佳答案

嗯,是的,你应该这样做,但如果你像你在示例中所做的那样使用 lambda 语法,我认为它不会起作用(我的意思是,处理程序将不会成功注销)。

如果我错了,请有人纠正我,但我相信这是真的,因为使用 lambda 语法有效地创建了一个新的 EventHandler<CustomerChangedEventArgs>。对象,在内存中有自己的位置。当您尝试删除此处理程序时,再次使用 lambda 语法,这会创建 另一个 新的 EventHandler<CustomerChangedEventArgs>对象,它不等于您创建的第一个对象;因此第一个永远不会被注销。

遗憾的是,我认为您实际上需要定义这样的方法:

DoReload(object sender, CustomerChangedEventArgs e) {
DoReload(); // your original overload, which doesn't actually care
// about the sender and e parameters
}

这样你就可以做到:

MessageBus<CustomerChangedEventArgs>.MessageReceived += DoReload;

之后:

MessageBus<CustomerChangedEventArgs>.MessageReceived -= DoReload;

关于c# - 使用静态类/事件作为应用程序消息总线是否存在缺陷,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2829703/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com