Java中的泛型(1)

     自java 1.5发行版本后,java中正式加入了泛型(Generic).它提供了一下的优势:
     1. 提供了更加严格的编译时类型检查. 例如,向声明为List<String>的列表中添加int值,直接在编译时就会出错.
     2. 消除了类型的cast. 同前面的列表中,取出来的直接就是String类型的元素.不再需要像之前的List一样,对取出的元素进行目标类型的cast.
     3.  实现了generic algorithm. 这是显而易见的. 
    不过,我们接着就会看到,java中的泛型是伪泛型的.这主要是由于编译器的Type Erasure机制导致的.


    为了应对这种运行时不可用的类型, 在运行时, 将对象的类型信息分为两种. 一种是类型信息是可用的,成为Reifiable type. 包括所有非泛型的类型.而另一种称为non-Reifiable type, 它是指类型信息在运行时比编译时类型更少的类型, 包括经过type erasure之后的类型. 
    另外, 对non-Reifiable type有两个限制: 不能出现在instanceof表达式中, 或者作为数组中的元素.
    由于Type Erasure而引发的伪泛型特征,导致了很多编程上的问题.
  • 首先,让我们看一个泛型继承的例子.
class Node<T>{
    void setData(T data);
}
class StringNode<String>{
    void setData(String data);
}
    由于type erasure机制,编译时会将父类的setData方法的参数类型erase为Object,从而导致StringNode并没有override setData方法.
    为了保证多态性, 编译器会生成bridge方法.针对上面的例子,会在StringNode类中生产以下的bridge方法.
void setData(Object data){
    this.setData((String)data;
}
  • 当一个参数化类型的变量(如List)指向一个非参数化的对象(如List)时.会引发所谓的Heap Pollution问题,例如可能会将Number实例添加到String的List中. 编译器会对这种情况发出unchecked warning. 常见的有以下两种场景:
    1. 混用raw type和parameterized type.
    2. 进行unchecked cast.

  • 泛型的非协变性(invariant). 引用Java官方文档的例图说明
    泛型的非协变性
    例如,有一个方法

void printList(List<Object> list);
   该方法是无法接收List<String>作为参数的.这是非协变性带来的继承性丢失. 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值