动态事件处理

时间:2011-06-12 23:11:25

标签: c# events memory-management

这是一个随机问题。

我有一个名为Monkey的对象,还有一个名为Banana的对象。 Banana暴露了一个名为Ripens的事件,Monkey对象订阅了这个事件。当触发Ripens事件时,Monkey调用其Consume()函数,该函数又会破坏Banana对象。

示例:

//And yes, I know this isnt real C# code. Just trying to get my point across and
//not necessarily be syntatically correct with this exmaple.
public class Banana
{
    public event Ripens;
}

public class Monkey
{
    public Monkey()
    {
        List<Banana> tree = new List<Banana>();
        for (int i = 0; i < 8; i ++)
        {
             tree.Add(new Banana());
             tree[i].Ripens += this.Consume;        
        }
    }

    public void Consume(Banana b)
    {
         tree.Remove(b);
         b.Destroy();
    }
}

所以我的问题是:在没有首先取消订阅其事件的情况下,猴子是否会为每个被破坏的香蕉留下内存。或者猴子中的事件处理程序是否与香蕉一起被破坏?

2 个答案:

答案 0 :(得分:3)

当猴子订阅香蕉时,香蕉现在有一个参考猴子,猴子没有香蕉。在你举例说明香蕉上升时,他们现在要收集垃圾。所以没有 - 猴子不会泄漏记忆。

答案 1 :(得分:0)

事件中的“内存泄漏”实际上发生在另一个方向。如果猴子超出范围,香蕉事件仍然会引用猴子上的事件委托,因此猴子不会收集垃圾。

要解决您的“每个”问题,是 - 事件处理程序是每个对象。因此,超出范围的多个订阅者仍然会通过事件发布者引用它们,导致它们不被垃圾回收。