Action 和 Func,匿名方法

#region Action 和 Func

/*
* 详细资料 https://www.cnblogs.com/kissdodog/p/5674629.html
*
* Action 引用一个void 返回类型的方法,可以传递 16 种不同类型的方法
* Action 没有泛型的话可以调用没有参数的方法
*
*
* Func 允许调用有返回类型的方法,和 Action 类似 也可以传递 16 种不同类型的方法和一个返回类型
* Func委托类型可以调用带返回类型且无参数的方法
* Func 调用带有一个参数的方法
*
*
* 区别:
* Func有返回类型;
* Action只有参数类型,不能传返回类型。所以Action的委托函数都是没有返回值的。
*
*
*/

  //class T
    //{
    //    //public static void DH()
    //    //{
    //    //    for (;;)Console.WriteLine("DH今天,你敲代码了吗?");
    //    //}

    //}
//***********************************
/*
 * Func
 * 
 * 代码思路:
 * 首先要有一个Main入口啥的,然后就是在 main 里面声明要排序的数组
 * 然后后就是要有排序的类(BubbleSorter)了
 * 将声明的数组通过 构造的委托类(Employee) 传递到这个方法(Sort)
 * 
 * public static void DH()
 * {
 *    for (;;)Console.WriteLine("DH,今天你思考了吗?");
 * }
 */
//class Program
//{
//    static void Main()
//    {
//        Employee[] employees =
//        {   new Employee("热爱生命                      ", 1),
//            new Employee("既然选择了远方                ", 2),
//            new Employee("我不去想是否能够成功          ", 1),
//            new Employee("便只顾风雨兼程                ", 3),
//            new Employee("就勇敢地吐露真诚              ", 6),
//            new Employee("我不去想能否赢得爱情          ", 4),
//            new Employee("我不去想身后会不会袭来寒风冷雨", 7),
//            new Employee("一切,都在意料之中            ", 12),
//            new Employee("我不去想未来是平坦还是泥泞    ", 10),
//            new Employee("既然钟情于玫瑰                ", 5),
//            new Employee("留给世界的只能是背影          ", 9),
//            new Employee("只要热爱生命                  ", 11),
//            new Employee("既然目标是地平线              ", 8)
//        };

//        foreach (var employee in employees)
//        {
//           Console.WriteLine(employee);
//        }
//    }
//}
////构造类,用来放置 Main 传递过来的值
//class Employee 
//{
//    public Employee(string name, decimal salary)
//    {
//        this.Name = name;
//        this.Salary = salary;
//    }
//    public string Name { get; }
//    public decimal Salary { get; private set; }
//    public override string ToString() => $"{Name}, {Salary:C}";
//    public static bool CompareSalary(Employee e1, Employee e2) =>
//      e1.Salary < e2.Salary;
//}
//class BubbleSorter
//{                                     
//    static public void Sort (IList sortArray, Func comparison)//sortArray 转递的是值  comparison 就是传递的方法的返回值
//    {
//        bool swapped = true;
//        do
//        {
//            swapped = false;
//            for (int i = 0; i < sortArray.Count - 1; i++)
//            {
//                if (comparison(sortArray[i + 1], sortArray[i]))
//                   //将 i+1 和 i 委托到 Employee 里面进行比较 注意,这个 i 代表的是 这个值在数组中的位置
//                {
//                    T temp = sortArray[i]; //将 这个 数 提取出来
//                    sortArray[i] = sortArray[i + 1];//赋值给 第 i+1 个
//                    sortArray[i + 1] = temp; //将 第 i 个数的值赋值给第i+1个
//                    swapped = true;
//                }
//            }
//        } while (swapped);
//    }
//}
//*************************************

/*
* 多播委托
*
* Action 这个委托可以被多次显式调用 ,委托里面包含多个方法的委托 就叫多播委托,类似于 Udp 那个多播协议
* 多播委托,可以按顺序调用多个方法。因此 委托的签名就必须返回void 否则 就只能得到最后一个方法的结果
*
*
* https://www.cnblogs.com/bianlan/archive/2013/01/18/2867065.html
*
*
*
* 和其他委托不一样,它可以调用多个方法,而其他委托只能调用一个(类似于 单线程,多线程 的区别,一顿吃一吨,一顿吃多吨)
*
* 支持运算符,就像这个
*
* 用于从委托中删除或添加方法的调用
*
*
* Action operation = K.M;
* operation += K.N;
* Action action3 = action1 + action2;
*
*/

  //class T
    //{
    //    static void Main()
    //    {             // Action 封装具有单个参数且不返回值的方法。
    //        Action a = K.M;//将 a 的值 委托到这个方法
    //        a += K.N;
    //        a += K.V;
    //        // 感觉像一个数组,不断调用数组里面的值
    //        //这里是和 Fun 地区别 对方法 可以像运算符一样, 
    //        G(a,2);
    //        G(a,3);
    //        G(a,5);
    //        G(a,8);
    //        //Console.WriteLine(Math.PI);
    //    }
    //    public static void G(Action action, double value)
    //    {
    //        Console.WriteLine();
    //        Console.WriteLine($"传递的值 {value}");
    //        action(value);//通过这个多播委托将值传递
    //    }
    //}
    //class K
    //{
    //    public static void M(double value)
    //    {
    //        double result = value * 2;
    //          Console.WriteLine($"乘2, 2 X {value} ={result}");
    //        //throw new Exception("哎呀,出错了。");//如果某一个环节报了异常,委托会停止 但有时候我并不希望这样 和他的执行顺序有关
    //    }                                                                                 
    //    public static void N(double value)
    //    {
    //        double result = value * value;
    //        Console.WriteLine($"{value} 的平方值为{result}");
    //    }
    //    public static void V(double value)
    //    {
    //        double result = Math.PI;
    //        Console.WriteLine($"乘圆周率 {value} X π = {result}");       
    //    }
    //}
    //*********************  利用 delegate 里面的 getinvoactionlist 这个方法  获取委托的链表
    //class T
    //{
    //    public static void V()
    //    {
    //        Console.WriteLine($"量子叠加态");
    //    }
    //    public static void W()
    //    {
    //        Console.WriteLine($"量子纠缠");
    //        throw new Exception();
    //    }
    //    public static void M()
    //    {
    //        Console.WriteLine("量子自旋");
    //    }
    //    static void Main()
    //    {
    //        Action  a = V;
    //        a += W;
    //        a += M;
    //        //如果某一个环节报了异常,委托会停止 但有时候我并不希望这样 
    //        // delegate 类 定义了一个 GetInvocationlist() 方法 返回一个 delegate 地对象数组, 
    //        //可以使用委托调用委托直接相关的方法 异常不影响
    //        Delegate[] delegates = a.GetInvocationList();//一个委托数组,其调用列表与此实例的调用列表相匹配。
    //        foreach (Action d in delegates)
    //        {
    //            try
    //            {
    //                d();    
    //            }
    //            catch (Exception)
    //            {
    //                Console.WriteLine("波函数坍塌");
    //            }
    //        }
    //    }
    //}
    //class K
    //{
    //}
    //************************************************************

/*

  • 匿名方法
  • 委托是用于引用与其具有相同标签的方法。换句话说,
  • 可以使用委托对象调用可由委托引用的方法。
  • 匿名方法(Anonymous methods) 提供了一种传递代码块作为委托参数的技术。
  • 匿名方法是没有名称只有主体的方法。
  • 在匿名方法中不需要指定返回类型,它是从方法主体内的 return 语句推断的。
  • 值得一提的是,在匿名方法中不能使用跳转语句 (break,goto,continue )跳转到匿名方法的外部,反之亦然

*/

  //class T
    //{
    //    static void Main()
    //    {
    //        string mid = ", middle part,";
    //        //Func anonDel = delegate (string param)//一个委托
    //        //{   
    //        //    param += mid;
    //        //    param += " and this was added to the string.";
    //        //    return param;
    //        //};
    //        //lambad 写法
    //        Func lambad = param =>
    //         {
    //             param += mid;
    //             param += "and this was added to the string.";
    //             return param;
    //         };
    //        Console.WriteLine(lambad("Start of string"));
    //    }
    /*
     * 在匿名方法的外面定义一个 字符串变量 mid ,并将变量添加到要传递的参数中,
     * 代码返回字符串的值,在调用委托时,把一个字符串作为参数传递,将返回的字符串输出到控制台上
     * 
     * 
     * 可以用 lambda 表示
     */**

// }
//*****************************************

//delegate void NumberChanger(int n);
//    namespace DelegateAppl
//    {
//        class TestDelegate
//        {
//            static int num = 10;
//            public static void AddNum(int p)
//            {
//                num += p;
//                Console.WriteLine("Named Method: {0}", num);
//            }
//            public static void MultNum(int q)
//            {
//                num *= q;
//                Console.WriteLine("Named Method: {0}", num);
//            }
//            static void Main(string[] args)
//            {
//                // 使用匿名方法创建委托实例
//                NumberChanger nc = delegate (int x)
//                {
//                    Console.WriteLine("Anonymous Method: {0}", x);
//                };
//                // 使用匿名方法调用委托
//                nc(10);
//                // 使用命名方法实例化委托
//                nc = new NumberChanger(AddNum);
//                // 使用命名方法调用委托
//                nc(5);
//                // 使用另一个命名方法实例化委托
//                nc = new NumberChanger(MultNum);
//                // 使用命名方法调用委托
//                nc(2);
//                Console.ReadKey();
//            }
//        }
//    }
#endregion

你可能感兴趣的:(c#)