美文网首页Java
关于,的学习记录

关于,的学习记录

作者: Hoker_ | 来源:发表于2018-11-19 20:49 被阅读0次
    查看Rx源码时,看到了<? extends T>的使用,看的一头雾水,在网上查询一段时间后,这里对<? extends T>和<? super T>做一下理解笔记。

    <? extends T>:是指 “上界通配符(Upper Bounds Wildcards)”
    <? super  T>:是指 “下界通配符(Lower Bounds Wildcards)”

    无论是上届还是下界,其描述主体都是T:

    • <? extends T>则表示T是最高的,也就是说,可以表示所有继承于T的(包括T)
    • <? extends T>则表示T是最低的,也就是说,可以表示所有T的父类(包括T)

    接下来对这些进行说明,先定义几个类:

        public class Animal{}
        public class Human extends Animal{}
        public class Coder extends Human{}
        public class Fish extends Animal{}
        public class Shark extends Fish{}
        public class Carp extends Fish{}
    
        public class Boat<T>{
            private T item;
            public Boat(T t){item=t;}
            public void set(T t){item=t;}
            public T get(){return item;}
        }
    

    其继承结构如下:


    继承结构

    Boat则是一个容器类,用来放这些动物们。
    首先,鲨鱼Shark显然也是鱼Fish,那么装鲨鱼的船(Boat<Shark>),和装鱼的船(Boat<Fish>),两者之间应该也能有一种关系:


    两种船

    简单点说,对于编译器而言:

    • Shark IS A Fish
    • SharkBoat IS NOT A FishBoat

    Sun公司为了解决这个问题,就提出了<? extends T>和<? super T>

    • 先说<? extends T>
      <? extends Fish>表示任何装鱼的船,这样就能有:
      <? extends Fish>
      那么至于上界:
      上界
    • 再说<? super T>
      <? super Fish>
      那么至于下界:
      下界

    现在说下<? extends T>,<? super T>的副作用

    • 上界<? extends T>不能往里存,只能往外取
      就拿Boat<? extends Animal>来说,他可以表示图里的所有的船,那存的时候编译器该如何考虑能存啥呢?是Human、还是Fish,显然这是两个东西,虽然都继承于Animal,所以编译器干脆就都不让存了,只能读,而读是没有问题的,因为不管怎么读都是Animal。
    • 下界<? super T>可以存,但往外取只能放在Object对象里
      就拿Boat<? extends Shark>来说,如图所示,可以保持其全部子类。然而对于取,显然就搞不清楚该用Shark、Fish还是Animal来表示了,明显的"Shark IS A Fish" 但 "Fish IS NOT A Shark" ,所以只能用Object这个所有的父类来展示了。
      下界set()
    总结:<? extends T>,<? super T>上界、下界,还是一个有点绕的概念,有时候也有点反直觉,加上实际项目中接触的少,所以不是很清楚,还是要理解记忆才行。

    相关文章

      网友评论

        本文标题:关于,的学习记录

        本文链接:https://www.haomeiwen.com/subject/uaiafqtx.html