new()和抽象基类的泛型类型约束

时间:2013-08-08 12:57:34

标签: c# generics abstract-class base-class

这里我们有一个简单的类层次结构,并使用type constraint new()

的泛型
public abstract class Base 
{
}

public class Derived : Base
{
}

public class TestClass
{
    private void DoSomething<T>(T arg) where T : new()
    {
    }

    public void TestMethod()
    {
        Derived d1 = new Derived();
        DoSomething(d1); // compiles

        Base d2 = new Derived();
        DoSomething(d2); // compile error
    }
}

代码无法在指定的行进行编译,错误为:

  

'Base'必须是具有公共无参数构造函数的非抽象类型,才能在泛型类型或方法'Foo.DoSomething(T)'

中将其用作参数'T'

这个错误是明确的,也是有道理的,但我希望编译器能够理解Base的所有派生(此时可以实例化)都有一个公共无参数构造函数。

这对编译器来说理论上是否可行?

2 个答案:

答案 0 :(得分:8)

唉,你必须明确给出类型

DoSomething<Derived>(d2);

理论上不可能创造一些抽象的东西

答案 1 :(得分:2)

new Constraint (C# Reference):

  

要使用新约束,类型不能是抽象的。

通话:

Base d2 = new Derived();
DoSomething(d2);

你其实在做:

Base d2 = new Derived();
DoSomething<Base>(d2);

由于Base是抽象的,因此发生编译错误。

所以,你必须明确地施展:

Base d2 = new Derived();
DoSomething((Derived) d2);

你怎么能确保编译器,任何人都放在那里,不是抽象的?

我看到的唯一方式是,如果我们得到一个关键字,例如“must-inherit-to-non-astract”,然后创建public must-inherit-to-non-abstract abstract class Base。在那之后,编译器可以肯定,如果你将基本实例放入你的方法,那实际上是一个子类,那是非抽象的,因此可以实例化。