c# - 转换为 void 返回委托(delegate)的匿名函数无法返回值

标签 c# lambda delegates anonymous-function

我有一个一般性问题:在下面的 C# 代码中,无法创建线程 tFour,并且编译器显示以下错误:“转换为 void 返回委托(delegate)的匿名函数无法返回一个值

代码

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace DelegatesAndLambda
{
    class Program
    {
        public static int ThrowNum(object a)
        {
            Console.WriteLine(a);
            return 2 * (int)a;
        }
        static void Main(string[] args)
        {
            Func<int> newF = delegate () { int x = ThrowNum(2); return x; };
            Thread tOne = new Thread( delegate () { int x = ThrowNum(2); });
            Thread tTwo= new Thread(()=> ThrowNum(2));
            Thread tThree = new Thread(() => newF());
            Thread tFour = new Thread(delegate () { int x = ThrowNum(2); return x;});
        }
    }
}

但是,创建线程 tOnetTwotThree 时不会出现错误。那么为什么 lambda 表达式允许传递带有返回值(非空)和多个参数的方法委托(delegate)(ThrowNum(2), newF()),而带有返回值的匿名方法( >delegate() { int x = ThrowNum(2); return x;}) 使用delegate关键字定义不能通过?我认为在这两种情况下我们都处理匿名方法?我确实知道 Thread 只接受两种类型的签名:void DoSomething() 和 void DoSomething(object o) 但主要区别是什么在使用相同(?)匿名方法初始化 tTwotFour 之间?我已经尝试寻找答案一段时间了,但没有成功。 谢谢

最佳答案

仅仅因为表达式主体的 lambda 表达式有结果并不意味着它已被使用。对于返回结果的 lambda 表达式来说,只要其主体是有效的语句表达式,就可以将其转换为具有 void 返回类型的委托(delegate)。这是一个简单的例子:

using System;

class Test
{
    static int Method() => 5;

    static void Main()
    {
        Action action = () => Method();
    }
}

没关系,因为 Method() 是一个有效的语句表达式。它只调用方法,而忽略结果。这无效,因为1 + 1不是有效的语句表达式:

// error CS0201: Only assignment, call, increment, decrement,
//               await, and new object expressions can be used as a statement
Action action = () => 1 + 2;

不存在表达式主体匿名方法这样的东西,所以事情变得更简单一些:您只是不能从匿名方法返回值并将该匿名方法转换为带有 void< 的委托(delegate)类型 返回类型。

C# 5 ECMA 标准的相关部分是 11.7.1:

Specifically, an anonymous function F is compatible with a delegate type D provided:

  • ...
  • If the body of F is an expression, and either D has a void return type or F is async and D has the return type Task, then when each parameter of F is given the type of the corresponding parameter in D, the body of F is a valid expression (w.r.t §12) that would be permitted as a statement-expression (§13.7).

关于c# - 转换为 void 返回委托(delegate)的匿名函数无法返回值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55296853/

相关文章:

java - "Annotated"lambda 表达式而不是具有单一应用方法的接口(interface)

c# - .NET Framework 支持空操作语法或单例

c# - CSharpCodeProvider 中的 Dll 引用仅在设置为 .NET 2.0 时才有效?

c# - 委托(delegate)给实例方法不能有 null 'this'

lambda - 计划中的关闭如何运作?

c# - 我应该使用 EventHandler<T> 和/或 EventArgs 委托(delegate)模式吗?

ios - 在 UICollectionReusableView 中未调用委托(delegate)

c# - 客户端验证错误

c# - 为 IList 优化 LINQ

python - 类型错误 : string indices must be integers using pandas apply with lambda