Java JDK 6是否允许非通用遗留代码?

时间:2012-02-24 16:49:59

标签: java generics

java JDK 6是否支持旧的非泛型集合,还是会在运行时破坏现有代码?

如果支持它,你必须启用吗?

例如:

List<Integer> list = new ArrayList<Integer>();
list.add(5);

Alpha a = new Alpha();
a.insert(list);

for (Integer integer : list) {
  System.out.println(integer);
}

非通用(遗留代码):

public class Alpha {
  public void insert(List list) { 
    list.add(new String("50"));
  }
}

这编译很好但在运行时断开。我认为它会运行正常,编译器会警告你。

2 个答案:

答案 0 :(得分:4)

泛型排序 - 仅在编译时存在。 (不完全;整个地方仍然有元数据,但对象类型本身不受影响,特别是支持ArrayList的数组仍然是Object[]。这在这里非常重要。)您可以始终使用泛型类型,就像它是非泛型类型一样 - 编译器会警告您,但类本身不能阻止您这样做。

您的代码中断了,因为您在此处隐式地将数组的每个元素转换为Integer:

for (Integer integer : list) {
    System.out.println(integer);
}

你如何期望在执行时处理?需要明确的是,编译后的代码大致相当于:

for (Iterator iterator = list.iterator(); iterator.hasNext(); ) {
    Integer integer = (Integer) list.next();
    System.out.println(integer);
}

想象一下,你处在一个没有仿制品的世界里,想想如果你在列表中得到一个String会怎么做(实际上你有Alpha)。完全相同的事情(ClassCastException)将出现 with 泛型。

答案 1 :(得分:2)

编译器会警告你这件事。

使用-Xlint选项运行javac以获取完整的详细信息。

  

警告:[未选中]未选中调用添加(E)作为原始类型java.util.List的成员   list.add(new String(“50”));

如果您想使用无类型(原始类型)列表,那么只需使用类似的遗留代码创建一个:

List list = new ArrayList();

但是当您将添加到List中的String转换为整数时,您的代码仍会在运行时失败。