4

假设

假设我们有一个接口,并且为该接口定义了以下扩展方法(它们的实现并不重要

public interface IPerson;

public class IPersonExtensionMethods
{
    public static bool SayHello(this IPerson talker, IPerson listener);
    public static bool SayGoodbye(this IPerson talker, IPerson listener);
}

问题

我们知道这两种扩展方法本质上是相同的,因为它们接受 2 个 type 参数IPerson和 return bool。现在,假设我们要将 1 个扩展方法分配给Func<IPerson, IPerson, bool>我们可以使用的类型的委托:

Func<IPerson, IPerson, bool> whatShouldWeSay;
if (sayHello)
{
    whatShouldWeSay = IPersonExtensionMethods.SayHello;
}
else
{
    whatShouldWeSay = IPersonExtensionMethods.SayGoodbye;
}

但是,如果我们将if语句转换为简写形式,如下所示:

Func<IPerson, IPerson, bool> whatShouldWeSay = (sayHello)
    ? IPersonExtensionMethods.SayHello
    : IPersonExtensionMethods.SayGoodbye;

我们得到编译错误信息:

无法确定条件表达式的类型,因为 'method.group' 和 'method.group' 之间没有隐式转换

问题

为什么会出现这个错误?是因为委托的性质是扩展方法吗?还是由于速记if语句如何确定结果类型?还是完全不同的东西?

4

1 回答 1

2

发生错误是因为在三元语句中,两个结果(真和假)都需要是相同的类型。常规方法也会发生同样的事情,而不仅仅是扩展方法。您需要将它们转换为目标类型:

Func<IPerson, IPerson, bool> whatShouldWeSay = (sayHello) 
    ? (Func<IPerson, IPerson, bool>)IPersonExtensionMethods.SayHello
    : (Func<IPerson, IPerson, bool>)IPersonExtensionMethods.SayGoodbye;

在三元语句中使用 null 时,我经历过一些这种情况,将强制转换null视为某种可空类型感觉很奇怪。这可以在此处以更简单的方式显示:

// Doesn't compile
int? a = true ? 10 : null;

// Compiles
int? a = true ? 10 : (int?)null;

我们得到以下编译器错误:

无法确定条件表达式的类型,因为 'int' 和 '<null>' 之间没有隐式转换

于 2013-03-28T11:42:19.220 回答