C# 如何取消注册“匿名”事件处理程序
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1348150/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How do I Unregister 'anonymous' event handler
提问by P.K
Say if I listen for an event:
假设我监听一个事件:
Subject.NewEvent += delegate(object sender, NewEventArgs e)
{
//some code
});
Now how do I un-register this event? Or just allow the memory to leak?
现在我如何取消注册这个事件?或者只是允许内存泄漏?
采纳答案by Reed Copsey
If you need to unregister an event, I recommend avoiding anonymous delegates for the event handler.
如果您需要取消注册事件,我建议避免事件处理程序的匿名委托。
This is one case where assigning this to a local method is better - you can unsubscribe from the event cleanly.
这是将它分配给本地方法更好的一种情况 - 您可以干净地取消订阅事件。
回答by Walt W
Do you need to un-register it for a reason other than leakage?
您是否需要出于泄漏以外的原因取消注册?
Regarding the "Or just allow the memory to leak" bit, when Subject is cleaned up by the Garbage Collector, your anonymous delegate should be cleaned up as well, so there shouldn't be a leak.
关于“或者只是允许内存泄漏”位,当垃圾收集器清理 Subject 时,你的匿名委托也应该被清理,所以不应该有泄漏。
回答by dtb
Give your instance of the anonymous delegate a name:
为您的匿名委托实例命名:
EventHandler<NewEventArg> handler = delegate(object sender, NewEventArgs e)
{
//some code
};
Subject.NewEvent += handler;
Subject.NewEvent -= handler;
回答by EKazakov
You can create method for unregistering from all listeners of event. This not exactly what you whant, but sometimes it can be helpfull. For example (this really works =)) :
您可以创建从事件的所有侦听器中注销的方法。这并不完全是您想要的,但有时它会有所帮助。例如(这确实有效=)):
class Program {
static void Main(string[] args) {
A someClass = new A();
someClass.SomeEvent += delegate(object sender, EventArgs e) {
throw new NotImplementedException();
};
someClass.ClearEventHandlers();
someClass.FireEvent();
Console.WriteLine("No error.");
}
public class A {
public event EventHandler SomeEvent;
public void ClearEventHandlers() {
Delegate[] delegates = SomeEvent.GetInvocationList();
foreach (Delegate delegate in delegates) {
SomeEvent -= (EventHandler) delegate;
}
}
public void FireEvent() {
if (SomeEvent != null) {
SomeEvent(null, null);
}
}
}
}
回答by apiguy
You need a name for your anonymous function, and then, you can only do it as long as the name is in scope:
您需要为匿名函数命名,然后,只要名称在范围内,您就可以这样做:
var handler = new EventHandler(delegate(object o, EventArgs e)
{
//do something...
};
Subject.NewEvent += handler;
// later on while handler is still in scope...
Subject.NewEvent -= handler;
回答by Ian
To remove the handler on first invocation:
在第一次调用时删除处理程序:
//SubjectType Subject = ..... already defined if using (2)
EventHandler handler = null;
handler = delegate(object sender, EventArgs e)
{
// (1)
(sender as SubjectType).NewEvent -= handler;
// or
// (2) Subject.NewEvent -= handler;
// do stuff here
};
Subject.NewEvent += handler;
回答by Benjol
There is another question (of mine) which goes into this in some (too much) detail: Weak event handler model for use with lambdas.
还有另一个问题(我的)在一些(太多)细节中涉及到这个问题:与 lambdas 一起使用的弱事件处理程序模型。
However, now that the ReactiveFrameworkhas come out, I'd seriously consider looking into that in this kind of situation.