zoukankan      html  css  js  c++  java
  • C# Action 和 Func 区别

    前言:

      1.委托是一个类,定义了方法的类型,使得可以将方法当作另一个方法的参数来进行传递。

         把一个 参数类型 返回值 相同 方法名不同 的方法当变量 的方法 叫委托。

       为了实现程序的六大设计中的开闭原则:解耦,对修改关闭,对扩展开放。逻辑分离。

          直接调用函数和使用委托调用函数的区别就是是否方便对外扩展。

         当我们窗体传值、线程启动时绑定方法、lambda表达式、异步等等情况下需要用到。

      2.事件是一种特殊的委托,本质就是委托,事件是回调机制的一种应用。

         当委托调用的函数达到某种条件时,可以通过回调通知调用者。

    一:委托的申明

      1. delegate  ,至少0个参数,至多32个参数,可以无返回值,可以指定返回值类型

           eg: public delegate int MethodDelegate(int x,int y);    //两个参数,返回int类型

      2. Action  ,至少0个参数,无返回值的泛型委托

        Action<int,string,bool> ,有传入int、string、bool类型的参数,无返回值的委托

        eg: public void Test<Test>(Action<T> action,T p) {   actoin(p);   }

      3. Func  ,至少0个参数,至多16个参数,必须有返回值的泛型委托

        Func<object,string,int> ,传入参数为object、string类型的参数,返回值为int的委托

        eg: public int Test<T1, T2>(Func<T1, T2, int>func,T1 a,T2 b){    return func(a, b);    }

      4.Predicate  ,有且只有一个参数,返回值只为 bool 类型

        predicate<int> 表示传入为int类型的参数,返回bool类型的委托。

        eg: public delegate bool Predicate<T>(T obj)

    二:委托的使用

      1. delegate 

        public delegate int MethodDelegate(int x,int y);
        private static MethodDelegate method;
        static void Main(string[]  args)
        {
          method = new MethodDelegate(Add);
          method(10,20);  
        }
           private static int Add(int x, int y)
        {
          return x +y;
        }

      2. Action 

        static void Main(string[] args)
        {
          Test<string>(Action, "Hello World");
          Test<string>(p => { Console.WriteLine("{0}", p); }, "Hello World" );
        }
        public static void Action(string s)
        {
          Console.WriteLine(s);
        }
        public static void Test<T>(Action<T> action,T p)
        {
          action(p);  
        }

      3. Func的使用

        static void Main(string[] args)
        {
          Test<int, int>(Fun, 100, 200);
        }
        public static int Test <T1, T2>(Func<T1, T2, int>func, T1 a,T2 b)
        {
          return func(a ,b);
        }
        private static int Fun(int a ,int b)
        {
          return a + b;
        }

      4. predicate 的使用

       static void Main(string[] args)
       {
          Point[] points = {
            new Point(100,200) ,
            new Point(250,375),
            new Point(150,250),
            new Point(275,395),
            new Point(295,450)
          };
          Point first = Array.Find(points,ProductGT10) ;
          Console.WriteLine("Found: X = {0},Y = {1}", frist.x, frist.Y);
       }
       private static bool ProductGT10(Point p)
       {
          if(p.X * p.Y > 100000)
          {
            return true;
          }
          else
          {
            return false;
          }
       }

    三:委托的清空

      1.在类中循环去除委托引用

        public MethodDelegate OnDelegate;
       public void ClearDelegate()
       {
          while(this.OnDelegate != null)
          {
            this.OnDelegate -= this.OnDelegate;
          }
       }

      2.在方法中查询出委托后去除

      public MethodDelegate OnDelegate;
      static void  Main(string[] args)
      {
        Program test = new Program();
        if(test.OnDelegate != null)
        {
           System.Delegate[] dels = test.OnDelegate.GetInvocationList();
           for(int 1 = 0; i < dels.Length; i++)
            {
             test.OnDelegate -= dels[i] as MethodDelegate;
           }
        }
      }

     PS:下面三种方式属于老式委托的使用,就不要用了。C#3.5之后都用  Action Func

     WithParaNoReturnEventHandler _WithParaNoReturnEventHandler = new WithParaNoReturnEventHandler(MyDelegate.SayChinese);
     MyDelegate.Say("张三",_WithParaNoReturnEventHandler);  //C#1.0 传统调用
     MyDelegate.Say("张三", delegate(string name) { Console.WriteLine("你好," + name); }); //C#2.0 匿名方法
     MyDelegate.Say("张三", (name) => { Console.WriteLine("你好," + name); }); //C#3.0 lambda表达式

      

  • 相关阅读:
    【洛谷P3469】[POI2008]BLO-Blockade
    【洛谷P3225】[HNOI2012]矿场搭建
    【洛谷P4568】[JLOI2011]飞行路线
    读入优化与输出优化模板
    7.29NOIP模拟赛
    【洛谷P3627】[APIO2009]抢掠计划
    【洛谷P1582】倒水
    运lucky
    【数据结构】浅谈倍增求LCA
    【题解】洛谷P4180 [BJWC2010] 严格次小生成树(最小生成树+倍增求LCA)
  • 原文地址:https://www.cnblogs.com/HansZimmer/p/13964475.html
Copyright © 2011-2022 走看看