无法使用可选参数推断泛型类型

时间:2012-03-27 22:13:00

标签: c# type-inference optional-parameters

鉴于以下方法签名,为什么在显式命名参数时,编译器无法自动推断出类型? Visual Studio 2010 SP1能够推断出类型,并且不会显示任何警告或错误。

IEnumerable<T> ExecuteCommand<T>(
    string commandText,
    string connectionName = null,
    Func<IDataRecord, T> converter = null) { ... }

static SomeClass Create(IDataRecord record) { return new SomeClass(); }

void CannotInferType() {
    var a = ExecuteCommand(
        "SELECT blah",
        "connection",
        converter: Test.Create);
}

void CanInferType() {
    var a = ExecuteCommand(
        "SELECT blah",
        "connection",
        Test.Create);
}

按照CannotInferType中的描述调用它,当尝试编译它时,编译器会发出error CS0411: The type arguments for method 'Test.ExecuteCommand<T>(string, string, System.Func<System.Data.IDataRecord,T>)' cannot be inferred from the usage. Try specifying the type arguments explicitly.,而CanInferType中所述的调用按预期工作。

如上所述,Visual Studio本身没有报告任何问题,变量a的intellisense按预期显示IEnumerable<SomeClass>但由于某种原因它不能编译。

1 个答案:

答案 0 :(得分:7)

这是C#4编译器中的一个错误。它已在C#5编译器中修复。

我怀疑这不是引起问题的可选参数 - 它是命名参数。尝试删除参数的默认值,我怀疑你仍然会遇到同样的问题。 (值得区分可选参数和命名参数 - 它们是两个独立的特征。它们经常一起使用,但肯定不一定。)

当我将此错误报告发送给Eric和Mads时,我得出的结论是:

using System;

class Test
{
    static void Foo<T>(Func<T> func) {}

    static void Main()
    {
        // Works fine
        Foo(() => "hello");

        // Type inference fails
        Foo(func: () => "hello");
    }
}

很高兴现在在C#5 beta编译器中运行