【问题标题】:How do i refactor this code by using Action<t> or Func<t> delegates如何使用 Action<t> 或 Func<t> 委托重构此代码
【发布时间】:2010-05-02 00:20:05
【问题描述】:

我有一个示例程序,它需要按特定顺序执行 3 个方法。 并且在执行每个方法之后,都应该做错误处理。现在我以正常方式执行此操作,不使用这样的委托。

类程序 { 公共静态无效 Main() {

        MyTest();
    }

    private static bool MyTest()
    {

        bool result = true;
        int m = 2;
        int temp = 0;

        try
        {
            temp = Function1(m);
        }
        catch (Exception e)
        {
            Console.WriteLine("Caught exception for function1" + e.Message);
            result = false;
        }

        try
        {
            Function2(temp);
        }
        catch (Exception e)
        {
            Console.WriteLine("Caught exception for function2" + e.Message);
            result = false;
        }

        try
        {
            Function3(temp);
        }
        catch (Exception e)
        {
            Console.WriteLine("Caught exception for function3" + e.Message);
            result = false;
        }

        return result;
    }

    public static int Function1(int x)
    {
        Console.WriteLine("Sum is calculated");
        return x + x;
    }

    public static int Function2(int x)
    {
        Console.WriteLine("Difference is calculated ");
        return (x - x);
    }

    public static int Function3(int x)
    {
        return x * x;
    }
}

如您所见,这段代码看起来很难看,有这么多的 try catch 循环,它们都在做同样的事情......所以我决定我可以使用委托来重构这段代码,以便可以全部推动 Try Catch成一种方法,使它看起来整洁。我在网上查看了一些示例,但无法确定我是否应该为此使用 Action 或 Func 代表。两者看起来相似,但我无法清楚地知道如何实现这一点。非常感谢任何帮助。我使用的是 .NET 4.0,所以我也允许为此使用匿名方法 n lambda 表达式

谢谢

【问题讨论】:

    标签: .net-3.5 delegates action func


    【解决方案1】:
    bool result = true;
    int m = 2;
    int temp = 0;
    
    var funcs = new Func<int, int>[]{
                              x =>
                                  {
                                      Console.WriteLine("Sum is calculated");
                                      return x + x;
                                  },
                              x =>
                                  {
                                      Console.WriteLine("Difference is calculated");
                                      return x - x;
                                  },
                              x => x * x
                          };
    
    temp = m;
    foreach (var func in funcs)
    {
        try
        {
            temp = func(m);
        }
        catch (Exception e)
        {
            Console.WriteLine("Caught exception:" + e.Message);
            result = false;
        }                
     }
    

    就像另一个答案所说,对于这个简单的例子来说,这可能有点过分了。但是在某些情况下它仍然很有用,例如,如果您想在每个步骤中实现一些重试逻辑(假设您正在做一些比计算值更复杂的事情)

    【讨论】:

    • 很好的答案(就像 Joel 的一样),但我不会将 Func&lt;&gt; 的数组命名为“动作”,因为这意味着 Action&lt;&gt; 的数组,可以是有点令人困惑,尤其是对于那些对两者之间的区别还有些模糊的人。我会使用“funcs”或“functions”。 @user330612:区别在于Func&lt;&gt; 返回一个值,而Action&lt;&gt; 没有。
    • 你能看看我的回复,看看我是否可以使用 func 来进一步简化这个吗?我现在 undstd diff bw 谓词、动作和函数 :) thnx
    【解决方案2】:

    感谢您的回复...我想出了这个解决方案

    @joel..thnx for the soln...正如你所看到的,抛出的异常不能终止程序......它在记录异常后会继续...... 这是我的代码 我仍然不知何故,觉得这可以/shd进一步重构。!我只是不知道如何:(

    任何进一步简化此的建议..

    注意:如果一个特定的函数抛出异常,整体结果应该是假的......但是应该继续执行其他函数以查看是否有任何其他函数失败......

    另外,这里提到的func只是为了说明,实际的方法更多的是cmplx

    class Program
    {
        public static void Main()
        {
            ExecuteTask task1 = Function1;
            ExecuteTask task2 = Function2;
            ExecuteTask task3 = Function3;
            bool result = true;
            int param1 = 2, param2 = 3, param3 = 4;
    
            MyTest(task1, ref result, ref param1);
            MyTest(task2, ref result, ref param2);
            MyTest(task3, ref result, ref param3);
    
            Console.WriteLine("final result is " + result.ToString());
            Console.ReadLine();
        }
    
        private delegate void ExecuteTask(ref int x);
    
        private static void MyTest(ExecuteTask task, ref bool result1, ref int param1)
        {
    
            try
            {
                task(ref param1);
            }
            catch (Exception e)
            {
                Console.WriteLine("Caught exception for " + e.Message);
                result1 = false;
            }
    
            return result1;
        }
    
        public static void Function1(ref int x)
        {
            Console.WriteLine("Sum is calculated");
            x = x + x;
        }
    
        public static void Function2(ref int x)
        {
            Console.WriteLine("Difference is calculated ");
            x = (2 * x - x);
        }
    
        public static void Function3(ref int x)
        {
            //Console.WriteLine("Product is calculated ");
            //x = x * x;
            throw new ArgumentOutOfRangeException();
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-06-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多