02.Java泛型通配符

1. 什么是通配符

类型通配符是指在方法调用时,使用符号“?”代替泛型类中规定的参数化类型。如以下所示(Java中的集合类型):

/**
  使用?做通配符,`ArrayList`和`ArrayList`都可以通过编译
*/
public void fun(ArrayList list){
  .....
}
public static void main(String[]args){
  ArrayList list1 = new ArrayList();
  ArrayList list2 = new ArrayList();
  fun(list1);  //编译通过
  fun(list2);  //编译通过
}

2. 无界通配符

类似于ArrayList这种,没有规定<>中参数化类型范围的,就是无界通配符

3. 有界通配符

使用extends或super修饰,规定<>中参数化类型范围的,就是有界通配符

  • 上界通配符
    语法:类/接口
    举例:
    class Animal {}
    class Cat extends Animal {}
    class MiniCat extends Cat {}
    
    public class Test {
      public static void main(String[] args) {
          ArrayList list1 = new ArrayList<>();
          ArrayList list2 = new ArrayList<>();
          ArrayList list3 = new ArrayList<>();
          upper(list1);  //编译不通过
          upper(list2);  //编译通过
          upper(list3);  //编译通过
      }
      /**
        表示只能接受Cat类或其子类作为泛型化参数
      */
      public static void upper(ArrayList list) {
          return;
      }
    }
    
  • 下界通配符
    语法:类/接口
    举例:
    class Animal {}
    class Cat extends Animal {}
    class MiniCat extends Cat {}
    
    public class Test {
      public static void main(String[] args) {
          ArrayList list1 = new ArrayList<>();
          ArrayList list2 = new ArrayList<>();
          ArrayList list3 = new ArrayList<>();
          upper(list1);  //编译通过
          upper(list2);  //编译通过
          upper(list3);  //编译不通过
      }
      /**
        表示只能接受Cat类或其父类作为泛型化参数
      */
      public static void bottom(ArrayList list) {
          return;
      }
    }
    

4. 有界通配符的插入读取限制

  • 含上界通配符的泛型类(以List为例)
    不能插入任何元素;
    可以读取T或T的子类。
  • 含下界通配符的泛型类(以List为例)
    可以读取到Object或者Object子类的对象;
    只能插入T类型对象

具体原因可参考链接1。另外与有界通配符相关的还有PECS原则,java.util.Collections里的copy方法就是用有界通配符实现的,满足PECS原则,具体解释可见链接2。

你可能感兴趣的:(02.Java泛型通配符)