• 泛型的约束与局限性


    内容来至java核心技术第9版第12章

    1. 不能用基本类型参数化实例类型

             即,没有Pair<int>,Pair<float>等类型

    2. 运行时类型检查只适用于原始类型,即JVM中不存在泛型或指定类型的泛型,导致无法进行某些判断

       ex.  if(a instanceof Pair<String>) ;  //--- error,无法判断a是Pair<String>的一个实例,因为运行时,类型擦出后变成pair<Object>,无法判断是否为String类型;

       同理,强制类型转换时也会出现同样的问题

       ex. Pair<String> p = (Pair<String>) a; //error, (Pair<String>) a运行时无法得知String类型,只能得到Pair<Object>,导致转换异常

       不同类型泛型擦出验证,以下代码说明JVM时是不区分泛型类型的,只保留原始类型

    Pair<String> p1 = ...;

    Pair<Integer> p2 = ...;

    if(p1.getClass()==p2.getClass()); //true

    3. 不能创建参数化类型的数组

    pair<String> p = new Pair<Sting>[10]; //error

      因为擦出机制,运行时无法区分p的引用内容(泛型具体类型),导致出现"猫插入狗列表"等业务逻辑上的异常,因此java得设计者阻止了这种应用.
    4. Varargs警告
      Varargs警告基于java不允许创建参数化类型数组,但是允许可变参数引用的情况(此时的参数为类型参数),以下理解为抑制ts数组的警告.

    @SafeVarargs

    Public static <T> void addAll(Collection<T> coll, T ... ts){ //ts理解为数组

      for(t:ts)coll.add(t);

    }

     
    5. 不能实例化类型变量,new T(...), new T[...], T.class, JVM时变成new Object(...), new Object[...], Object.class,业务上不可能存在这样的调用,所有java阻止了这种应用.   但是通过引用传递的方式是可以到达某种类似效果的,比如:

    Public static <T> pair<T> makePair(Class<T> cl){

      try{

        return new Pair<>(cl.newInstance,cl.newInstance);

      }catch(Exception e){

        return null;

      }

    }

    ...

    Pair<String> p = Pair.makePair(String.class);

     
    6. 禁止使用带有类型参数的静态域或方法,JVM时可能会遇到数据插入混乱问题,java阻止了这种应用.
    7. 不能抛出或捕获泛型类的实例,甚至连扩展Throwable都是不允许的.

    public class Problem<T> extends Exception{ //error, can't extends Throwable

      ...

    }

    public static <T extends Throwable> void doWork(Class<T> t){

      try{

        do Work;

      }catch(T e){ //error, can't catch type variable

        Logger.global.info(...)

      }

    }

    //不过在异常规则允许下是可以用到类型参数的

     public static <T extends Throwable> void doWork()T t throw T //OK

    {...}

     
    8.注意擦出后的冲突,所以不能再泛型类中建立类似equals(T x)这样的方法,因为擦出后与Object.equals(object obj)冲突了(相同的方法参数与方法名).
     当两个接口是同一个接口的不同参数化时,要强行限制一个类或类型变量不能同时成为这两个类的子类,即不能同时extends或implements这两个接口(有可能与中间合成的桥方法冲突).
  • 相关阅读:
    window phone7中自定义listbox或scrollviewer滚动条样式
    windows phone7中使用bing中文地图和Google地图
    window phone7中listbox,ItemsControl等项渲染速度慢的解决方案
    window phone list box使用收藏,mvvm ItemsControl数据绑定
    RSA的密钥把JAVA格式转换成C#的格式
    自定义控件
    【03】flask之url_for函数及过滤器使用
    【01】flask之入门及安装
    js 弹出层
    插入排序_排序算法_算法
  • 原文地址:https://www.cnblogs.com/runwulingsheng/p/5144119.html
Copyright © 2020-2023  润新知