【发布时间】:2012-08-13 20:27:03
【问题描述】:
如果我有一个 lambda,例如 () => { throw new Exception(); },则不清楚它是否有返回类型。因此,它可以(隐式)转换为Action 和Func<object>(或任何其他Func<T>)。这是因为,根据 C# 4 规范的 §6.5 匿名函数转换:
[A] 委托类型
D与提供的匿名函数F兼容:
…
如果
D有一个void返回类型并且F的主体是一个语句块,那么当[...]F的主体是一个有效的语句块,其中没有返回语句指定一个表达式。如果
D有一个非空返回类型并且F的主体是一个语句块,当[...]F的主体是一个有效的语句块时,它的端点不可到达每个return语句都指定一个表达式,该表达式可以隐式转换为D的返回类型。
但是,如果我有一个方法的两个重载,其中一个具有 Action 类型的参数,另一个具有 Func<object> 类型的参数,并且我从上面传递 lambda,则使用 Func<object> 重载。为什么?在这种情况下,规范的哪一部分说Func<object> 优于Action?
我看过 §7.5.3.2 更好的函数成员,但这并没有解释它。
【问题讨论】:
-
如果您使用符号
delegate { throw new Exception(); }代替 lambda 语法,在()括号中省略参数列表,则该匿名函数可以匹配 any 委托我猜的签名,也包括例如EventHandler和Action<object, EventArgs>. -
@JeppeStigNielsen 是的。在这种情况下,确实没有规则可以将它们作为方法参数来消除歧义,所以你会得到一个编译错误。
标签: c# lambda overload-resolution