是否有事件发生/失去听众的事件?

时间:2012-11-29 05:52:41

标签: c# events .net-3.5

  

可能重复:
  Is it possible to subscribe to event subscriptions in C#?

搜索有关事件事件的信息并不容易。我只是希望这不是因为它无法完成。我只是希望答案是“有一个事件,”或其他一些手段。

我正在处理一个事件,在这个事件中,倾听事件的成本相对较高。 (手表必须放在另一个系统中,我要跟踪它,包括跟踪要跟踪的内容和COM开销。)

因此,除非我知道有什么需要,否则我真的不想看这个事件。

这样做的简单方法是:

public class MyThing
{
    public delegate void MyEventHandler(object sender, MyEventArgs ea);
    public event MyEventHandler Change;

    public void StartWatching()
    {
        ...
    }

    public void StopWatching()
    {
        ...
    }
}

这是以这种方式使用的:

var thing = new MyThing();
thing.Change += this.thing_Change
thing.StartWatching();

thing.Change -= this.thing_Change
thing.StopWatching();  // Hopefully nothing else is watching...

但这并不像我想的那么优雅。我可以将thing.Change += x替换为thing.StartWatching(x),然后开始观看,反过来会检查是否Change == null,但如果完全可以完成,我会喜欢它优雅的活动模式。

3 个答案:

答案 0 :(得分:1)

听起来像custom event accessor可能就是你想要的。

int count = 0;

event EventHandler MyThing.Change
{
    add
    {
        lock (Change)
        {
            if (count == 0)
            {
                StartWatching();
            }

            count++;
            Change += value;
        }
    }
    remove
    {
        lock (Change)
        {
            count--;
            if (count == 0)
            {
                StopWatching();
            }

            Change -= value;
        }
    }
}

答案 1 :(得分:1)

尝试将您的事件声明为属性并使用添加/删除访问者

class YourClass
{
    public event EventHandler<EventArgs>  MyEvent
    {
        add
        {
            // Add new subscriber code here
        }

        remove
        {
            // Remove subscriber code here
        }
    }
}

答案 2 :(得分:1)

您可以覆盖事件的添加/删除方法并在那里完成工作。

public class MyThing
{
    public delegate void MyEventHandler(object sender, MyEventArgs ea);

    private MyEventHandler _change;
    public event MyEventHandler Change
    {
       add 
      { 
          var previousChange = _change;
          _change += value; 
          if (previousChange == null)
          {
             StartWatching();
          }
       }
       remove 
       { 
          _change -= value;
          if (_change == null) 
          {
             StopWatching();
          }
       }
    }

    public void StartWatching()
    {
        ...
    }

    public void StopWatching()
    {
        ...
    }
}

目前,这不是线程安全的,但你可以很容易地做到这一点。