(三)泛型-协变和逆变的概念-泛型是不可变的

学习泛型的时候遇到了协变和逆变的概念,其实从某种程度上来说,这是可以略过的,这种概念的东西乍一看很容易让人不知所云。之所以说可以略过,是因为协变和逆变是一个单独存在的概念,然后恰巧在泛型的某些情况中有所体现。
更多的时候,大家更喜欢使用数组举例,然后说数组是协变的。本文将先讲述协变和逆变的概念,然后再举出数组的协变的例子,然后是泛型的协变和逆变的例子。

协变和逆变是函数中的概念

首先设计到一个函数的概念,协变和逆变是表示 函数变量关系与函数关系的特性表述。
比如 1<2 , 然后 函数f(x)=x+1,那么 f(1)< f(2),再进一步拓展假如 1<=2,并且f(1)<=f(2),那么我们就说 f(x)协变 的。
再比如,1<2,f(x)=-x,这个时候就有 f(1) >f(2) ,再进一步扩展,1<=2,并且f(1)>=f(2),那么我们就说f(x)是逆变的。

数组就像一种函数,变量是某种Java类或者接口,数组是协变的

在 Java 中,向上转化和向下转化都是基于具体类或者接口来说的,比如Integer、Number、Object,那么Integer[]是不是一个单独的类型呢?是的,数组是新组合起来的类型,即由某种类或接口产生了一种变化,等同于数学中称之为函数的东西。

比如这里,IntegerNumber 的子类,那么经过一个变化之后,比如 Integer[]Number[]之后,二者会是什么关系呢?如下代码:

    @Test  
    public void test(){  
        Number[] array1=new Number[1];//合法  
        Number[] array2=new Integer[1];//合法  
        //Integer[] array3=new Number[1];//编译报错  
    }  

Java 多态中有一个子类概念,显然,new Number[1] 在这里类似于 Number[] 的子类,然后第三行是编译报错,如果把数组看做一个函数,那么满足 x<=y , f(x)<=f(y),所以数组是协变的,第三行表示数组不是逆变的。

泛型是不可变的

上文已经说了,协变与逆变的概念,以及数组是协变的。

泛型是不可变的,即 ArrayList<Number>ArrayList<Integer>并不具有 NumberInteger那样的关系,这是因为泛型是在编译期检测类型合法性的,而在实际运行期类型被擦除了,所以在泛型看来 ArrayList<Number>ArrayList<Integer> 是两种不同的类型。
如下代码会编译报错:

    @Test  
    public void test1(){  
        ArrayList<Number> list=new ArrayList<Integer>();//编译报错  
    }  
泛型实现协变和逆变的特性-其他形式的泛型-彩蛋

不好意思哦,其他形式的泛型“犹抱琵琶半遮面”,下一篇见哦~

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值