【问题标题】:C# Delegate Lambda [duplicate]C# 委托 Lambda [重复]
【发布时间】:2017-06-26 07:37:08
【问题描述】:

请考虑以下几点:

private static string Sub(int anInt)
{
    return anInt.ToString();
}

private static void Test()
{
    const int anInt = 100;

    Func<int,string> aFunc = Sub;

    //why does Task<string> task = Task.Run(aFunc(anInt)); not compile?
    Task<string> task = Task.Run(() => aFunc(anInt));

    Console.WriteLine(task.Result);
}

这段代码编译得很好。为什么行

Task<string> task = Task.Run(aFunc(anInt));

不编译?

有没有办法在没有 Lambda 表达式的情况下传递委托调用?

我错过了什么?

【问题讨论】:

  • 你得到的错误是告诉你究竟为什么它不能编译。

标签: c# lambda delegates


【解决方案1】:

错误状态

无法从“字符串”转换为“System.Action”

通过传递aFunc(anInt),您基本上传递了方法调用的结果——一个字符串。可以这样想 - 如果您在 Func 变量的名称之后键入 () - 您正在当场执行它。

如果你想传递一个带有参数的 Func,你必须按照你说它为你编译的方式来做:

Task<string> task = Task.Run(() => aFunc(anInt));

...因为这会将您的调用包装在一个新的可执行文件中,然后运行该可执行文件。

查看this answer了解更多详情。

【讨论】:

    【解决方案2】:

    我们来分析一下这一行:

    Task<string> task = Task.Run(aFunc(anInt));
    

    此行无法编译,因为编译器将aFunc(anInt) 理解为“执行aFunc(anInt),然后在调用Task.Run() 时使用其返回值作为参数”。

    本质上,您正在尝试将字符串强制输入Task.Run。相当于试试这个:

    Task<string> task = Task.Run("blah");
    

    上述行将产生完全相同的错误消息。

    【讨论】:

      【解决方案3】:

      您不能这样做,因为您调用的是 aFunc 而不是引用它。

      如果您开始将参数传递给一个方法,而不是简单地给出它的名称,您就是在调用它。

      要引用一个方法,只给出名称,不要传递任何参数。就像你在这里所做的一样:

      Func<int,string> aFunc = Sub;
      

      您没有将任何参数传递给Sub,因为您只是在说“我的意思是那个方法称为Sub”。

      现在让我们看看错误的代码:

      Task<string> task = Task.Run(aFunc(anInt));
      

      Task.Run 接受Action 类型的参数,但您给它的返回值是aFunc,它是一个字符串。看看为什么它现在会产生错误?

      你不能说“我的意思是这个方法,用anInt的参数调用”。这简直是​​不可能的。您必须为此创建一个 lambda。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2012-08-27
        • 1970-01-01
        • 2013-06-10
        • 1970-01-01
        • 2011-10-23
        • 2011-09-24
        • 2012-09-14
        相关资源
        最近更新 更多