美文网首页
? extends T 和? super T使用场景

? extends T 和? super T使用场景

作者: Uhiroshi | 来源:发表于2022-08-05 19:39 被阅读0次

最近在看阿里开发手册时看到<? extends T >和<? super T>,以及PECS原则。
记录一下我的理解。
简单理解就是

  • ? extends T与?super T两者用于泛型对象的读取和插入操作:
  • ? extends T子类限定,被其修饰的对象只能进行读取操作,不能增删。
  • ? super T超类限定,被其修饰的对象只能进行增删操作,不能读取。

测试类

class human{}
class man extends human{
  private String name;
  man(){}
  man(String name){this.name = name;}
  public String getName(){return name};
}
class xiaoming extends man{
  private String name;
  xiaoming(String name){
        this.name = name;
  }
  public String getName(String name){
      return name;
  }
}

测试调用方法

public void test(){
    //超类限定对象  可以添加本身和自己的子类
    List<? super man> list = new ArrayList<man>();
    list.add(new man("man1"));
    list.add(new xiaoming("qwe"));

    List<man> manList = new ArrayList<>();
    manList.add(new man("asd"));
    manList.add(new man("qwe"));
    testExtends(manList);
    testSuper(manList);    
}

子类限定
对于传入的泛型对象只能查看,不能删改。被? extends T修饰的泛型对象,不能添加其本身,子类或者父类以及其他任一一种对象。

public void testExtends(List<? extends man> list) {
    for(man m : list) {
        System.out.println(m.getName());
    }
    System.out.println(list.get(0).getName());
    System.out.println(list.isEmpty());
}

超类限定
对传入的参数可以进行修改,但是不能查看。例如下面的getName()方法就会爆红,因为传来的List<? super man> man List是Object类型,且有? super man T限定,即使加了强制转换(man)也无法识别。

public void testSuper(List<? super man> list){
    System.out.println("-----进入super-----");
    list.add(new man("qwee"));
    list.remove(0);
    System.out.println((man)list.get(0));
    //上面这条语句如果加上.getName()就会报红
    //因为(man)list.get(0)不能被当成man类型的对象
}
运行结果 com.example.postest.post是我的包名

将? extends T 和 ? super T运用到实际中。? extends T 修饰的对象只负责读取,? super T修饰的对象只负责插入。就是PECS(Producer Extends, Consumer Super)原则。

接着是官方的标准用法,java.util.collection中的copy方法


copy方法

相关文章

网友评论

      本文标题:? extends T 和? super T使用场景

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