无法将源类型转换为目标类型编译错误

本文关键字:目标 类型 编译 错误 类型转换 | 更新日期: 2023-09-27 18:00:42

我有一个简单的类

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,我不知道为什么会出现编译错误。请帮我理解我做错了什么。

谢谢,Esen

无法将源类型转换为目标类型编译错误

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

类是不变的,这意味着如果您声明ClassB<T>,那么在创建实例时:

ClassB<T1> obj = new ClassB<T2>

则CCD_ 2必须与CCD_ 3是完全相同的类。

你可以使用接口来绕过这一点,例如将你的代码更改为以下代码,它就会编译:

...
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本身。然而,使用协方差(和反方差)存在风险,这就是为什么泛型类在默认情况下是不变的。