2013-04-01 42 views
2

我想知道c#中事件的确切用途是什么。我仍然在学习c#的过程中,所以我可能会错过一些东西,但是可以使用代表。
在这个例子中,我编写了一个类,其方法的计数范围是从0到2^64,每次达到一千个倍数时都会引发一个事件。下面是代码:在c中使用事件关键字#

namespace EventDelegate 
{ 
class Program 
{ 
    static void Main(string[] args) 
    { 
     EventRaiserClass _eventraiser = new EventRaiserClass(); 
     _eventraiser.handler = SomeEventHandler; 
     _eventraiser.handler += AnotherEventHandler; 
     _eventraiser.Loop(); 
     Console.Read(); 
    } 

    static void SomeEventHandler(object sender, EventArgs args) 
    { 
     Console.WriteLine("Event raised"); 
    } 

    static void AnotherEventHandler(object sendr, EventArgs args) 
    { 
     Console.WriteLine("Event raised (Another handler)"); 
    } 
} 

public delegate void Handler(object sender, EventArgs args); 

class EventRaiserClass 
{ 
    public Handler handler; 
    public void Loop() 
    { 
     for (long i = 0; i < Int64.MaxValue; i++) 
     { 
      if ((i % 1000) == 0) 
      { 
       EventArgs args = new EventArgs(); 
       RaiseEvent(args); 
       System.Threading.Thread.Sleep(1000); 
      } 
     } 
    } 

    private void RaiseEvent(EventArgs args) 
    { 
     if (handler != null) 
      handler(this, args); 
    } 
} 

}

什么会区别已经如果我宣布了handler委托变量是这样public event Handler handler的事件。
对不起,如果我有点模糊或缺少一些明显的东西,但我只是想知道在使用event而不是使用后面发生的其他事情是否会发生,而不仅仅是为了便于阅读。

+1

可能重复(http://stackoverflow.com/questions/803242/understanding-events-and-event-handlers-in-c-sharp) –

+3

查看http://csharpindepth.com/Articles/Chapter2/Events.aspx –

+0

谢谢,我来看看。 –

回答

2

活动和代表非常相似,但事件受到更多限制,原因很充分。

在你的代码中,你可以从外面用_eventraiser.handler做各种事情。尽管如此,你不应该做大部分的事情。

考虑这条线:

_eventraiser.handler = SomeEventHandler; 

如果你使用的代表,你就必须检查每一个尝试,如果委托是null附加的事件处理程序的时间,然后用=初始化它,如果它是不是null,你只需要处理程序与+=。如果你忘记了一个初始化,你会得到一个空引用异常,如果你输入太多,你会覆盖所有以前的东西。

如果您在本示例中使用事件而不是委托,则不必执行任何操作,实际上甚至不能执行此操作。与代表你甚至可以把它,然后传递给其他类,这可能是非常危险的。

Invoke也是如此,以及您可以对委托人执行的所有其他操作:它们不适用于事件。外部课程中唯一可以做的事情是+=-=,就是这样。您可以将它们视为具有特殊公共接口的代理人,并具有复杂的getter和setter。

(活动也有专门的addremove语法,但是这是一个相当不常用的功能)了解事件和事件处理程序在C#]的

+0

感谢您的帮助。我回到代码,并委托一个事件之后,我在这一行'_eventraiser.handler = SomeEventHandler;'这会尝试覆盖所有以前订阅的方法错误。 :-) –