1.数组不能向上转型

    1. package com.package15;
    2. class Fruit{}
    3. class Apple extends Fruit{}
    4. class Jonathan extends Apple{}
    5. class Orange extends Fruit{}
    6. public class CovarianArrays {
    7. public static void main(String[] args) {
    8. //创建了一个apple类型的数组,并把他指向Fruit的引用
    9. Fruit[] fruits=new Apple[10];
    10. fruits[0]=new Apple();//可以存放Apple和其子列
    11. fruits[1]=new Jonathan();
    12. try {
    13. fruits[0] = new Fruit();//宿主无法向上转换
    14. }catch (Exception e){
    15. System.out.println("数组无法向上型");
    16. }
    17. try {
    18. fruits[2]=new Orange();
    19. }catch (Exception e){
    20. System.out.println("不能存放Apple继承关系外的对象");
    21. }
    22. }
    23. }
    1. 我们创建了一个Apple类型的数组,并把他指向了Fruit的引用,所以只能忘这个数组中存放Apple及其子类。虽然我们可以在编译阶段放入Fruit Orange类型的对象,但在运行时候会抛出异常的<br /> 这是我们可以使用泛型,将这种错误在编译阶段显示出来
    1. // ArrayList<Fruit> objects = new ArrayList<Apple>();//error
    1. 在这里 Apllelist不是Fruitlist.两者在类型上是不等价的。所以说在泛型中正在的问题是我们在谈论容器持有的类型而不是容器的类型。一个容器的持有类型是Apple另一个是Fruit所以两者在类型上根本是不想等的<br /> 验证:
    1. List<Apple> apples = new ArrayList<>();
    2. //1行2行等同 ArrayList<Fruit> objects = new ArrayList<Apple>();
    3. List<Fruit> fruits1 = new ArrayList<>();
    4. apples=fruits1;//错误的
    5. List<Apple> apples1 = new ArrayList<>();
    6. apples=apples1
    7. }

    2.通配符
    2.1<? extends ClassType>
    特性:
    使用此通配饰符的集合无法添加内容。只能去添加null或者调用参数为Object类型的方法.get方法必须在集合已经初始化时才可以调用。

    1. package com.package15;
    2. import java.util.ArrayList;
    3. import java.util.List;
    4. class Fruit{}
    5. class Apple extends Fruit{}
    6. class Jonathan extends Apple{}
    7. class Orange extends Fruit{}
    8. public class ExtendDemo {
    9. public static void main(String[] args) {
    10. List<? extends Fruit> fruits = new ArrayList<Apple>();
    11. fruits.add(new Apple());
    12. fruits.add(new Fruit());
    13. fruits.add(new Orange());
    14. fruits.add(null);
    15. fruits.contains(new Apple());
    16. fruits.indexOf(new Apple());
    17. }
    18. }
    1. 我们可以将List<? extends Fruit> 读作任何从Fruit继承的类型列表。一个类的子类可以是无数个,所以此时谁也不知道List<? extends Fruit> 要表示的是那个具体的类型。虽然我们在后面指定类型为Apple,但是却不知道将Apple向上转型为谁?所以编译器会为我们报错。<br />2.2<? super ClassType>超类通配符,由某个特定类的基类来确定的<br /> 在集合中使用次通配符就可以写入元素了。<br />
    1. package com.package15;
    2. import java.util.ArrayList;
    3. import java.util.List;
    4. class Fruit{}
    5. class Apple extends Fruit{}
    6. class Jonathan extends Apple{}
    7. class Orange extends Fruit{}
    8. public class ExtendDemo {
    9. public static void main(String[] args) {
    10. List<? super Apple> fruits = new ArrayList<>();
    11. fruits.add(new Apple());
    12. fruits.add(new Jonathan());
    13. fruits.add(new Fruit());//报错
    14. fruits.add(new Orange());//报错
    15. fruits.add(null);
    16. }
    17. }
    1. <? super Apple>中,以Apple来当做元素存放的下届,任何继承此列或此类的类型对象都可以存放到集合中,当想集合中添加FruitOrange时候,由于Orange没有继承Apple Fruit又是Apple的父类。所以当存放的时候碰到了Apple这个下限。不能将他们添加到元素中。