<? extends …>与<? super …>区别与理解

导读:本篇文章讲解 <? extends …>与<? super …>区别与理解,希望对大家有帮助,欢迎收藏,转发!站点地址:www.bmabk.com

一、<? extends …>

extends指上界通配符,示例中指的是所有Fruit类及其派生的子类。
在这里插入图片描述
对该通配符指示的容器进行写入操作(set),就像收到一个包裹,上面写了包裹里都是水果,但编译器并不事先知道具体是哪一种水果,如果里面是香蕉,但放入了一个苹果就会造成错误,所以编译器禁止这种操作。

public void Func( List <? extends Fruit> temp) 
{
  temp.set(...); //compile time error
}

而对该通配符指示的容器进行读取操作(get),就像从包裹里拿一个水果,传递给一个Fruit对象。编译器无需关心到底是什么水果,因为Fruit类一定是该水果的超类,用Fruit对象调用的方法一定是该水果定义了的,不会发生错误。

二、super

super指下界通配符,示例中指的是所有Fruit类及其超类。
在这里插入图片描述

对该通配符容器进行读取(get)操作,就像收到一个包裹,里面是水果或者食物,但编译器不知道到底是什么,如果拿出一个并传递给一个Fruit对象,就有可能发生”超类对象被子类引用调用一个不存在的方法”,造成错误。

public void Func( List <? super Fruit> temp) 
{
  Fruit a = temp.get();   //compile time error . 
                          //if not so,assume return an Food obj, refered by a Fruit variable,it seems to be ok
  //a.Fruitcolor();      // Food obj don't have a method defined in Fruit class, oop! 
}

而对其进行写入(set)操作,就像向包裹中放入东西,只要保证放入的东西是Fruit的子类,编译器无需直到容器具体的类型,就可以保证容器不会“调用一个不存在的方法”

三、总结

总结起来,编译器检查,如果可以确保总是用超类变量引用其子类对象,那么之后通过该变量调用的方法,一定在子类中已被定义。
而一旦出现用子类变量引用超类对象的情况,尽管其后也许并不一定发生错误,但编译器无法确定这一点,只能触发编译错误。

摘自:
作者:BJChangAn
链接:https://www.jianshu.com/p/447e13647824
来源:简书

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/67255.html

(0)
小半的头像小半

相关推荐

极客之音——专业性很强的中文编程技术网站,欢迎收藏到浏览器,订阅我们!