简体   繁体   English

我必须取消订阅所有活动处理程序吗?

[英]Must I unsubscribe all event handlers?

From the Designer in VS let's say you double click on a button and it generates this Click event handler. 在VS中的Designer中,假设您双击按钮并生成此Click事件处理程序。

the subscription code is in the designer.cs. 订阅代码在designer.cs中。

I was wondering, in the dispose the Form MUST I unsubcribe the event ? 我想知道,在处理表格中我必须取消订阅活动吗?

Also, all control that are in the form will it be disposed when the forms disposes? 此外,表格中的所有控件都将在表格处理时处理? it actually call dispose on each control recursively? 它实际上是递归调用每个控件上的dispose?

You don't need to unhook the event on Dispose if you are hooking your own event. 如果要挂钩自己的事件,则无需在Dispose上取消挂钩事件。

You only need to worry about it if you are hooking an event in another object. 如果要在另一个对象中挂钩事件,则只需要担心它。 The reason for this is that event hooks keep a reference alive to the subscriber. 这样做的原因是事件挂钩将引用保持为订阅者。 If you fail to unhook, then you won't get garbage collected as long as the observable is still alive. 如果你没有解开,只要观察者还活着,你就不会收集垃圾。

When you hook your own event, you have a reference to yourself, which is circular, therefore you don't need to worry about it. 当你挂钩自己的事件时,你有一个自己的引用,这是循环的,因此你不需要担心它。

I have come to support more loosely coupled event patterns for this reason. 由于这个原因,我来支持更松散耦合的事件模式。 This is the #1 place for memory leaks in .Net. 这是.Net内存泄漏的第一名。 I prefer the Event Aggregator pattern (with weak events ). 我更喜欢Event Aggregator模式( 弱事件 )。

On the question "will it actually call dispose on each control recursively?", the answer is yes. 关于“它实际上是否会递归调用每个控件上的处理?”的问题,答案是肯定的。

A simple test can be done by putting a breakpoint in the Dispose method of a control. 可以通过在控件的Dispose方法中放置断点来完成一个简单的测试。

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();

        this.Controls.Add(new SuperButton());
    }
}

public class SuperButton : Button
{
    protected override void Dispose(bool disposing)
    {
        //Place breakpoint on the line below
        base.Dispose(disposing); 
    }
}

只要事件处理程序代码是表单本身,那么您就不需要取消订阅事件 - 因为控件没有悬空事件处理程序,因为表单本身会被破坏

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM