C#:'lambda expression'和'lambda expression'之间没有隐式转换?

Svi*_*ish 37 c# lambda

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

说什么?有人可以向我解释这个编译错误吗?这是产生它的代码:

    protected override Func<System.IO.Stream> GetStream()
    {
        return someBool
            ? () => EmbeddedResourceExtractor.GetFile("SomeFile1.ext")
            : () => EmbeddedResourceExtractor.GetFile("SomeFile2.ext");
    }
Run Code Online (Sandbox Code Playgroud)

这不是:

    protected override Func<System.IO.Stream> GetStream()
    {
        return () => EmbeddedResourceExtractor.GetFile("SomeFile1.ext");
    }
Run Code Online (Sandbox Code Playgroud)

这两个都没有:

    protected override Func<System.IO.Stream> GetStream()
    {
        if(someBool)
            return () => EmbeddedResourceExtractor.GetFile("SomeFile1.ext");
        return () => EmbeddedResourceExtractor.GetFile("SomeFile2.ext");
    }
Run Code Online (Sandbox Code Playgroud)

Jon*_*eet 49

条件表达式的类型必须作为一个整体推断 - 并且lambda表达式总是必须转换为特定的委托或表达式树类型.

在后两个例子中,编译器知道它试图将lambda表达式转换为什么.在第一个示例中,它首先尝试计算出整个条件表达式的类型.

但是其中一个分支的演员阵容就足够了:

protected override Func<Stream> GetStream()
{
    return someBool
        ? (Func<Stream>)
          (() => EmbeddedResourceExtractor.GetFile("SomeFile1.ext"))
        : () => EmbeddedResourceExtractor.GetFile("SomeFile2.ext");
}
Run Code Online (Sandbox Code Playgroud)

塞尔吉奥的修复(现已删除,但包括在下面)将起作用,如果someBool在调用函数时很乐意评估:

protected override Func<Stream> GetStream()
{
    return () => someBool
          ? EmbeddedResourceExtractor.GetFile("SomeFile1.ext")
          : EmbeddedResourceExtractor.GetFile("SomeFile2.ext");
}
Run Code Online (Sandbox Code Playgroud)

根据时间的不同,有各种不同的方法来修复你实际给出的例子,例如

protected override Func<Stream> GetStream()
{
    string name = someBool ? "SomeFile1.ext" : "SomeFile2.ext";
    return () => EmbeddedResourceExtractor.GetFile(name);
}
Run Code Online (Sandbox Code Playgroud)

我猜你的真实代码更复杂.

在某些方面,C#的类型推断不能更强大,这是一种耻辱 - 但它已经非常复杂了.

  • 除了必须在括号中包装第一个分支之外,这是有效的...希望他们可以在将来更好地使C#的类型推断更好.虽然,它已经非常好了=) (2认同)