【问题标题】:Cannot convert source type to target type compilation error无法将源类型转换为目标类型编译错误
【发布时间】:2015-09-17 20:28:57
【问题描述】:

我有这个简单的课程

public class Program
{
    private static void Main(string[] args)
    { 
        ClassB<ClassA> objA = new ClassB<ClassA>();

        ClassB<ITestA<MyDTO>> objB = new ClassB<ClassA>();

    }
}


public class ClassB<T>
{
    ///some code here
}


public interface ITestA<T>
{
    ///some code here
}

public class MyDTO
{
    ///some code here
}

public class ClassA : ITestA<MyDTO>
{
    ///some code 
}

这行代码

ClassB<ITestA<MyDTO>> objB = new ClassB<ClassA>();

出现编译错误

Cannot implicitly convert type 'ClassB<ClassA>' to 'ClassB<ITestA<MyDTO>> 

由于 ClassA 实现了 ITestA,我不知道为什么会出现编译错误。请帮助我理解我做错了什么。

谢谢, 埃森

【问题讨论】:

  • 只有接口支持方差。你不能那样做。

标签: c# generics type-conversion


【解决方案1】:

这是由于泛型的一个相当复杂的特性,称为variance

类是不变的,也就是说如果你声明ClassB&lt;T&gt;,那么在创建实例的时候:

ClassB<T1> obj = new ClassB<T2>

那么T1 必须与T2 完全相同。

您可以使用接口来解决这个问题,例如将您的代码更改为以下内容,它会编译:

...
public class Program
{
    private static void Main(string[] args)
    {
        ClassB<ClassA> objA = new ClassB<ClassA>();

        IClassB<ITestA<MyDTO>> objB = new ClassB<ClassA>();

    }
}


public interface IClassB<out T>  // <- note the out before T
{
    //some code here
}
public class ClassB<T> : IClassB<T>
{
    //some code here
}
...

在这种情况下,IClassB 被声明为协变,这意味着它可以处理给定的派生类T,而不需要T 本身。但是,使用协变(和逆变)存在风险,这就是泛型类默认不变的原因。

【讨论】:

    猜你喜欢
    • 2014-10-27
    • 2015-09-21
    • 1970-01-01
    • 1970-01-01
    • 2016-01-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多