为什么通用数组代码编译干净?

时间:2012-12-04 18:34:48

标签: java generics

在重构遗留代码并开始使用泛型后,我发现这些函数看起来像这样:

T[] splitXXX() {
   //blah blah
}

产生大量的类强制转换,因为jdk并不真正支持泛型类型的数组。 我想知道 - 为什么这段代码在java中干净利落地编译?它与向后兼容性有关吗? (如果我能在编译时发现这个错误而不是在运行时发现这个错误,那么本来可以节省大量的调查时间)。我错过了什么?

2 个答案:

答案 0 :(得分:0)

如果类型变量仅出现在返回类型中,则非常危险。例如

public static <T> T foo(){ ... }

// usage
String s = foo();
Integer i = foo();

编译器认为,如果程序员将T分配给String,他可能知道他在做什么,所以推断T=String是非常安全的。哎呀,根本没有任何限制,foo()的结果可以分配给任何类型。

但程序员可能并不总是知道他在做什么;他依靠强类型编译器来捕获他可能无意中犯下的一些输入错误。

答案 1 :(得分:0)

仅仅因为你做不到new T[...]并不意味着你不能拥有类型T[]的变量,就像你不能做new T()并不意味着你不能拥有变量输入T

完全可能拥有包含返回T[]的方法的正确代码:

class Something<T> {
    T[] foo;
    Something(T[] in) { foo = in; }
    T[] splitXXX() { return foo; }
}
  

产生大量的类强制转换,

好吧,如果它产生异常,那就意味着你做错了什么。您没有告诉我们什么代码产生异常或任何东西,但您可能正在进行在代码中无效的强制转换。