繁体   English   中英

C#Lambda中的变量参数

[英]Variable parameters in C# Lambda

是否可以使用C#lambda / delegate来获取可以使用Dynamic-invoke调用的可变数量的参数?

我在这种情况下使用'params'关键字的所有尝试都失败了。


来自答案的工作代码更新:

delegate void Foo(params string[] strings);

static void Main(string[] args)                       
{
    Foo x = strings =>
    {
        foreach(string s in strings)
            Console.WriteLine(s);
    };

    //Added to make it clear how this eventually is used :)
    Delegate d = x;

    d.DynamicInvoke(new[]{new string[]{"1", "2", "3"}});
}

将参数直接传递给DynamicInvoke()时它不起作用的原因是DynamicInvoke()需要一个对象数组,一个元素用于目标方法的每个参数,编译器会将一个数组解释为params数组到DynamicInvoke()而不是目标方法的单个参数(除非将其转换为单个object )。

您还可以通过传递包含目标方法的parameters数组的数组来调用DynamicInvoke() 外部数组将被接受为DynamicInvoke()的单个params参数的参数,内部数组将被接受为目标方法的params数组。

delegate void ParamsDelegate(params object[] args);

static void Main()
{  
   ParamsDelegate paramsDelegate = x => Console.WriteLine(x.Length);

   paramsDelegate(1,2,3); //output: "3"
   paramsDelegate();      //output: "0"

   paramsDelegate.DynamicInvoke((object) new object[]{1,2,3}); //output: "3"
   paramsDelegate.DynamicInvoke((object) new object[]{}); //output: "0"

   paramsDelegate.DynamicInvoke(new []{new object[]{1,2,3}}); //output: "3"
   paramsDelegate.DynamicInvoke(new []{new object[]{}});      //output: "0"
}

不,但它确实采取的任何参数都可以是一个数组。

没有更多细节,这就是它的长短。

不,但有一点帮助,你几乎可以伪造它:

object[] Params(params object[] args) { return args;}

// :

Action<string, object[]> CWL = 
                  (format,  args) => Console.WriteLine(format, args);

CWL("{0}, {1}", Params(1,2));

添加到Mark的答案,我将创建一个扩展方法来清理一下:

static DynamicInvokeParams(this ParamsDelegate delegate, params object[] args)
{
  delegate.DynamicInvoke(new [] {args});
}

然后你只需要说:

paramsDelegate.DyanamicInvokeParams(1, 2, 3);

我觉得有一个非常重要的一点,这里没有讨论,那就是如果你已经定义了一个带有params参数的委托类型,那么根本就没有必要调用DynamicInvoke 我可以想象的唯一场景是,如果您有自定义类型的委托,并且将它作为参数传递给接受Delegate参数并在上调用DynamicInvoke某个方法。

但是让我们看一下OP更新中的这段代码:

delegate void Foo(params string[] strings);

static void Main(string[] args)                       
{
    Foo x = strings =>
    {
        foreach(string s in strings)
            Console.WriteLine(s);
    };

    x.DynamicInvoke(new[]{new string[]{"1", "2", "3"}});
}

上面的DynamicInvoke调用完全是多余的。 最后一行阅读更为明智:

x("1", "2", "3");

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM