2016-04-20 38 views
0

在C#中可以有一个方法接受一个委托,有零,1或许多参数?C#lamba作为参数的方法

在下面的方法中,当我在对话框中单击“是”时,我希望能够做某种事情。我为此使用了一个委托,但目前它只接受不带参数的方法。

有可能有多种方法来做到这一点,如传递一个包含参数的泛型类,但是最好的方法是什么? C#是否提供了一些开箱即用的方式以优雅的方式来完成此操作?

public static bool ShowCustomDialog(string message, 
             string caption, 
             MessageBoxButtons buttons, 
             XafApplication application, 
             Action onYes = null) 
    { 
     Messaging messageBox = new Messaging(application); 
     var dialogResult = messageBox.GetUserChoice(message, caption, buttons); 
     switch (dialogResult) 
     { 
      case DialogResult.Yes: 
       onYes?.Invoke(); 
       break; 
     } 
     return false; 
    } 
+0

没有,这是不可能创建accespts的参数的任何任意数目的FUNC如'行动','ActionT1,T2,...>'的方法。 – HimBromBeere

回答

4

直接解决你的问题,这就是为什么你使用lambda表达式:

ShowCustomDialog("Hi!", "Greeting", MessageBoxButtons.YesNo, 
       () => DoSomething(myArgument, anotherArgument)); 

这是在像依赖注入技术的核心 - ShowCustomDialog方法应该不知道有这个动作任何东西,除了事实上它不需要输入ShowCustomDialog方法本身。如果ShowCustomDialog必须通过一些参数,则可以使用Action<SomeType>而不是Action

在封面下,编译器创建一个包含要传递的参数的类,并创建一个代表该类的实例。因此,它是(主要是),相当于手工编写这样的事:

class HelperForTwoArguments 
{ 
    bool arg1; 
    string arg2; 

    public HelperForTwoArguments(bool arg1, string arg2) 
    { 
    this.arg1 = arg1; 
    this.arg2 = arg2; 
    } 

    public void Invoke() 
    { 
    DoSomething(arg1, arg2); 
    } 
} 

// ... 

ShowCustomDialog("Hi!", "Greeting", MessageBoxButtons.YesNo, 
       new HelperForTwoArguments(myArgument, anotherArgument).Invoke); 

这种能力一直在从一开始的.NET框架,它只是得到了更容易使用与匿名委托和lambda表达式特别。

但是,我不得不说我根本没有看到任何指向你的“帮手”的方法。与做这样的事情有什么不同?

if (ShowCustomDialog("Hi!", "Greeting", MessageBoxButtons.YesNo)) 
    DoSomething(myArgument, anotherArgument); 
+0

我猜OP需要通过任意任意数量的参数,而不是只有一个。所以这也应该为他工作:'(x)=> x.DoSomething(myArgument,anotherArgument));' – HimBromBeere

+2

@HimBromBeere你包装在一个委托中有零参数 - 正是我首先提出的。要么这个方法必须知道这些参数,然后让那些不符合签名的代理没有意义,或者它不关心参数,然后它只需要'Action'。 – Luaan

+0

是的,这是我正在寻找我现在可以传递方法ShowCustomDialog,它不必知道什么样的方法是什么。 – Barsonax