几行代码帮你搞懂C#中的协变与逆变

几行代码帮你搞懂C#中的协变与逆变

什么是协变与逆变?简单说就是在泛型编程中扩大和缩小使用范围, 达到灵活编程的效果. 比如可以将一个Dog类作Animal类使用, 也可以将一个Animal类作Dog类使用,下面通过几行代码来说明.
创建一个Animal类

    internal class Dog:Animal
    {
    
    
    }

创建一个Dog类,继承自Animal类

    internal class Animal
    {
    
    
    }

写一个Test类, 该类继承自ITest接口

public interface ITest<in TIn, out TOut>
{
    
    
    void show(TIn value);
    TOut Get();
}

internal class Test<T1, T2> : ITest<T1, T2>
{
    
    
    public void show(T1 value)
    {
    
    
        Console.WriteLine(typeof(T1).Name);
    }
    public T2 Get()
    {
    
    
        Console.WriteLine(typeof (T2).Name);
        return default(T2);
    }
}

我们在主函数中使用

//父类: Animal子类: Dog
//协变:子类可以赋值给父类,用关键字out声明
//逆变:父类可以赋值给子类,用关键字in声明


ITest<Dog, Animal> testl = new Test<Dog, Animal>();//正常传递参数,Dog是入参,Animal是出参
ITest<Dog, Animal> test2= new Test<Dog, Dog>();//协变
ITest<Dog, Animal> test3 = new Test<Animal, Animal>();//逆变
ITest<Dog, Animal> test4 = new Test<Animal, Dog>();//逆变+协变

ITest<Animal, Dog> test5 = new Test<Animal, Dog>();//正常传递参数
/*
错误,ITest类第一个类型参数是in;代表逆变,逆变可以将父类赋值给子类,而这里却将子类赋值给父类,逻辑相悖
ITest<Animal, Dog> test6 = new Test<Dog, Dog>();
*/

/*
错误, ITest类第二个类型参数是out,代表协变,协变可以将子类赋值给父类,而这里却将父类赋值给子类,逻辑相悖
ITest<Animal, Dog> test7 = new Test<Animal, Animal>();
*/

/*
ITest类第一个类型参数是in,代表逆变,逆变可以将父类赋值给予类,而这里却将于类斌值给父类,逻辑相悖
ITest类第二个类型参数是out,代表协变,协变可以将子类赋值给父类,而这里却将父类赋值给于类,逻辑相悖
ITest<Animal, Dog> test8 = new Test<Dog, Animal>();
*/

猜你喜欢

转载自blog.csdn.net/weixin_45589116/article/details/136633799