zoukankan      html  css  js  c++  java
  • 5. 第二章:C#委托和事件之事件

    第二章:C#委托和事件

     

    第二节:事件

    事件其实没什么不好理解的,声明一个事件不过类似于声明一个委托类型的变量而已。

     1     public class MyTestClass
     2     {
     3         //定义委托
     4         public delegate void MyDelegateHandler(string param);
     5 
     6         //构造函数
     7         public MyTestClass()
     8         {
     9             this.MyDelegateHappened += this.MyInsideDelegateMethod;
    10         }
    11 
    12         //内部方法
    13         private void MyInsideDelegateMethod(string param)
    14         {
    15             Console.WriteLine("I am running inside the class "MyClass" -> void MyInsideDelegateMethod(string param)");
    16             Console.WriteLine(param);
    17         }
    18 
    19         //执行
    20         public void Execute(string param)
    21         {
    22             this.OnMyDeletateHappened(param);
    23         }
    24 
    25         //事件
    26         public event MyDelegateHandler MyDelegateHappened;
    27         protected virtual void OnMyDeletateHappened(string param)
    28         {
    29             MyDelegateHandler handler = this.MyDelegateHappened;
    30             if (handler != null)
    31             {
    32                 handler(param);
    33             }
    34         }
    35     }

    调用:

     1         static void Main(string[] args)
     2         {
     3             Console.WriteLine("Only the inside method will be executed!");
     4             //实例化
     5             MyTestClass myTestClass = new MyTestClass();
     6             myTestClass.Execute("Hello, world!");
     7             Console.WriteLine();
     8 
     9             Console.WriteLine("The outside method will be added to the delegate logic!");
    10             //新增外部委托的方法
    11             myTestClass.MyDelegateHappened += MyOutsideDelegateMethod;
    12             myTestClass.Execute("Hello, world!");
    13             Console.WriteLine();
    14 
    15             Console.WriteLine("The outside method will be removed from the delegate logic!");
    16             //去除外部委托的方法
    17             myTestClass.MyDelegateHappened -= MyOutsideDelegateMethod;
    18             myTestClass.Execute("Hello, world!");
    19             Console.ReadLine();
    20         }
    21 
    22         private static void MyOutsideDelegateMethod(string param)
    23         {
    24             Console.WriteLine("I am running ouside the class "Program" -> void MyOutsideDelegateMethod(string param)");
    25             Console.WriteLine(param);
    26         }

    运行结果:

    Only the inside method will be executed!

    I am running inside the class "MyClass" -> void MyInsideDelegateMethod(string param)

    Hello, world!

     

    The outside method will be added to the delegate logic!

    I am running inside the class "MyClass" -> void MyInsideDelegateMethod(string param)

    Hello, world!

    I am running ouside the class "Program" -> void MyOutsideDelegateMethod(string param)

    Hello, world!

     

    The outside method will be removed from the delegate logic!

    I am running inside the class "MyClass" -> void MyInsideDelegateMethod(string param)

    Hello, world!

     

    相信有部分读者看到这里,会想起C#里面常见的EventHandler

    a. 不带参数的

            public event EventHandler MyEventHappened;
            protected virtual void OnMyEventHanppened()
            {
                EventHandler handler = this.MyEventHappened;
                if (handler != null)
                {
                    handler(this, EventArgs.Empty);
                }
            }

    其实,请看EventHandler实际的本质是什么:(F12 Go To Definition)

     1 #region Assembly mscorlib.dll, v4.0.0.0
     2 // C:Program Files (x86)Reference AssembliesMicrosoftFramework.NETFrameworkv4.5mscorlib.dll
     3 #endregion
     4 
     5 using System.Runtime.InteropServices;
     6 
     7 namespace System
     8 {
     9     // Summary:
    10     //     Represents the method that will handle an event that has no event data.
    11     //
    12     // Parameters:
    13     //   sender:
    14     //     The source of the event.
    15     //
    16     //   e:
    17     //     An System.EventArgs that contains no event data.
    18     [Serializable]
    19     [ComVisible(true)]
    20     public delegate void EventHandler(object sender, EventArgs e);
    21 }

    b. 带参数的

            public event EventHandler<EventArgs> MyEventHappened;
            protected virtual void OnMyEventHanppened(EventArgs args)
            {
                EventHandler<EventArgs> handler = this.MyEventHappened;
                if (handler != null)
                {
                    handler(this, args);
                }
            }
     1 #region Assembly mscorlib.dll, v4.0.0.0
     2 // C:Program Files (x86)Reference AssembliesMicrosoftFramework.NETFrameworkv4.5mscorlib.dll
     3 #endregion
     4 
     5 namespace System
     6 {
     7     // Summary:
     8     //     Represents the method that will handle an event.
     9     //
    10     // Parameters:
    11     //   sender:
    12     //     The source of the event.
    13     //
    14     //   e:
    15     //     An System.EventArgs that contains the event data.
    16     //
    17     // Type parameters:
    18     //   TEventArgs:
    19     //     The type of the event data generated by the event.
    20     [Serializable]
    21     public delegate void EventHandler<TEventArgs>(object sender, TEventArgs e);
    22 }

    带参数的EventArgs,可以我们自己定义继承类去传递我们需要的数据:

     1     public class MyEventArgs : EventArgs
     2     {
     3         private string _param;
     4 
     5         public MyEventArgs(string param)
     6         {
     7             this._param = param;
     8         }
     9 
    10         public string Param
    11         {
    12             get { return this._param; }
    13         }
    14     }

    定义event的时候:

    1         public event EventHandler<MyEventArgs> MyEventHappened2;
    2         protected virtual void OnMyEventHappened2(MyEventArgs args)
    3         {
    4             EventHandler<MyEventArgs> handler = this.MyEventHappened2;
    5             if (handler != null)
    6             {
    7                 handler(this, args);
    8             }
    9         }

    上述两个示例说明:EventHandler本质,依然是一个delegate!只不过它是由系统定义好了而已,现在编程者常用这种方式,便于使用。

    代码:

     1     public class MyTestClass2 {
     2         public void Execute(string param)
     3         {
     4             this.OnMyEventHappened(new MyEventArgs(param));
     5         }
     6 
     7         public event EventHandler<MyEventArgs> MyEventHappened;
     8         protected virtual void OnMyEventHappened(MyEventArgs args)
     9         {
    10             EventHandler<MyEventArgs> handler = this.MyEventHappened;
    11             if (handler != null)
    12             {
    13                 handler(this, args);
    14             }
    15         }
    16     }
    17 
    18     public class MyEventArgs : EventArgs
    19     {
    20         private string _param;
    21 
    22         public MyEventArgs(string param)
    23         {
    24             this._param = param;
    25         }
    26 
    27         public string Param
    28         {
    29             get { return this._param; }
    30         }
    31     }

    调用:

     1         static void Main(string[] args)
     2         {
     3             MyTestClass2 myTestClass = new MyTestClass2();
     4             myTestClass.MyEventHappened += MyTestClass_MyEventHappened;
     5             myTestClass.Execute("Hi~");
     6 
     7             Console.ReadLine();
     8         }
     9 
    10         private static void MyTestClass_MyEventHappened(object sender, MyEventArgs e)
    11         {
    12             Console.WriteLine(e.Param);
    13         }

    运行结果:
    Hi~

    此程序中:myTestClass.Execute("Hi~");其实也可以由类的内部调用——这样做,就可以做到类的实例内部触发事件,然后做到“通知”外部注册时逻辑被执行的效果!

    综上所述,大家是不是对委托和事件有更清晰的认识了呢?

     

  • 相关阅读:
    Linux运维工程师需要掌握什么才能胜任工作呢
    我眼中的Linux系统和红帽RHCE认证
    Linux系统从零到高手的进阶心得
    我在大学毕业后学习Linux系统的心得经验
    装RAC跑脚本报错
    Oracle rac11g 安装报INS41112
    Oracle升级11.2.0.3-11.2.0.4(Windows)
    防存储掉线安装监控软件
    跨平台迁移数据库windows-Linux
    linux crontab -e生成日期格式
  • 原文地址:https://www.cnblogs.com/Min-min/p/5095650.html
Copyright © 2011-2022 走看看