静态事件如何与C#中的非静态事件进行比较?

我刚刚意识到静态事件的存在 – 我很好奇人们如何使用它们。 我想知道相对比较如何与静态与实例方法保持一致。 例如,静态方法基本上是一个全局函数。 但我总是将事件与对象实例联系起来而我在全球范围内无法思考它们。

这里有一些代码可以参考它是否有助于解释:

void Main() { var c1 = new C1(); c1.E1 += () => Console.WriteLine ("E1"); C1.E2 += () => Console.WriteLine ("E2"); c1.F1(); } // <>+D() public delegate void D(); // +<>E1 // +<><>E2 // +F() // <> // <>E1 // <>E2 public class C1 { public void F1() { OnE1(); OnE2(); } public event D E1; private void OnE1() { if(E1 != null) { E1(); } } static public event D E2; static private void OnE2() { if(E2 != null) { E2(); } } } 

在消息传递方面可以考虑大部分OOP。

方法调用是从调用者到被调用者(携带参数)的消息和带有返回值的消息。

事件是从源到订户的消息。 因此可能涉及两个实例,一个发送消息,另一个接收消息。

对于静态事件,没有发送实例(只是一个类型,可能是也可能不是类)。 仍然可以将接收者实例编码为委托的目标。

警惕静态事件。 请记住,当一个对象订阅一个事件时,该事件的发布者将持有对该对象的引用。 这意味着您必须非常小心明确取消订阅静态事件,因为它们会使订户永远保持活着,也就是说,您最终可能会遇到内存泄漏的托管等效项。

如果您不熟悉静态方法

您可能已经熟悉静态方法。 如果你不是,一个容易理解的区别是你不需要创建一个对象的实例来使用静态方法,但你需要创建一个对象的实例来调用非静态方法。

一个很好的例子是System.IO.Directory和System.IO.DirectoryInfo类。

Directory类提供静态方法,而DirectoryInfo类则不提供。

这里有两篇描述它们的文章,供您自己看一下。

http://visualcsharptutorials.com/2011/01/system-io-directory-class/

http://visualcsharptutorials.com/2011/01/system-io-directoryinfo-class/

现在开始静态事件 ……

然而,在野外很少见到静态事件。 很少有案例我认为opf在哪里我真的想要使用一个,但有一篇CodeProject文章确实显示了一个潜在的用途。

http://www.codeproject.com/KB/cs/staticevent.aspx

这里的关键思想取自解释(我添加粗体指出相关文本):

我们将此属性视为一个单独的对象,并确保一次只有一个实例。 所有交易实例都知道在需要时可以在哪里找到它。 但是有一个很好的区别。 交易不需要知道汇率发生的变化,而是通过请求当前值来使用最后更改的值。 例如,当我们想要实现一个应用程序时,这是不够的,其中用户界面立即对UI特征(如字体)的变化作出反应,就像它必须实时发生一样。 如果我们可以在Font类中使用名为currentFont的静态属性,并将静态方法更改为所有实例,让他们知道何时需要更新其外观,那将非常容易。

作为.NET开发人员,我们接受过使用断开连接模型的培训。 想想ADO.NET与经典ADO相比。 在VB6应用程序中,您可以使用允许以下function的数据控件:如果您在PC上运行应用程序,当另一台PC上的某人编辑数据时,网格中的数据将会更新。

这不是.NET开发人员习惯的。 我们已经习惯了断开连接的模型。 静态事件可实现更“连接”的体验 。 (即使这种经历是我们不再习惯的东西。)

有一些见解,请查看此链接http://www.codeproject.com/KB/cs/staticevent.aspx

可以使用静态事件

  • 当没有实例存在时
  • 为所有现有实例做一些多播事件……
  • 当你有一个可以触发事件的静态类时……

但是应该使用它们来进行评论…请参阅讨论http://groups.google.com/group/microsoft.public.dotnet.languages.csharp/browse_thread/thread/2ac862f346b24a15/8420fbd9294ab12a%238420fbd9294ab12a?sa=X&oi=groupsr&start= 1 NUM = 2

更多信息

http://msdn.microsoft.com/en-us/library/8627sbea.aspx
http://dylanbeattie.blogspot.com/2008/05/firing-static-events-from-instance.html
http://www.nivisec.com/2008/09/static-events-dont-release.html

静态成员不是“全局的”,它们只是类的成员,而不是类实例 。 对于事件和方法,属性,字段等都是如此。

我不能举一个使用静态事件的例子,因为在大多数情况下我通常不会发现静态成员是有用的。 (他们倾向于暗示反模式,比如辛格尔顿。)