Ble*_*eek 20 java compiler-construction generics
实际上,问题应该是
Creating an array of generic anything.
Run Code Online (Sandbox Code Playgroud)
为什么编译器不能处理它呢?
以下内容将被标记为错误 - 无法创建通用数组.
List<MyDTO>[] dtoLists = {new ArrayList<MyDTO>(), anExistingDtoList};
Run Code Online (Sandbox Code Playgroud)
要克服这一点,我需要
List<MyDTO>[] dtoLists = (List<MyDTO>[])Array.newInstance(ArrayList.class, 2);
dtoLists[0] = new ArrayList<MyDTO>();
dtoLists[1] = anExistingDtoList;
Run Code Online (Sandbox Code Playgroud)
那么,为什么编译器不能将第一种情况转换为第二种情况呢?
我确实认识到泛型是编译时确定的而不是运行时确定的,而数组是运行时确定的,因此需要确定类型才能创建数组.
编译器设计人员会遇到哪些技术/逻辑障碍会妨碍他们实现这一目标?
这个问题纯粹是哲学上的,关于语言正交性吗?如果是这样,这种行为将如何违反语言正交性?
这是一个复杂性的问题吗?解释复杂性.
我希望我的问题的答案能让我更好地了解java编译器在涉及泛型时的行为.
旁注:来吧,停止触发快乐.答案通用列表数组 不回答我的问题.为什么编译器不能自发地执行转换?
实际上Java确实为varargs创建了通用数组,所以你可以这样做
List<MyDTO>[] dtoLists = array(new ArrayList<MyDTO>(), anExistingDtoList);
@SafeVarargs
static <E> E[] array(E... array)
{
return array;
}
Run Code Online (Sandbox Code Playgroud)
至于为什么禁止显式通用数组创建,它与类型擦除有关.(同样的问题存在于上述解决方案中,但受到抑制@SafeVarargs
)但是它是值得商榷的; 有不同的方法来处理问题,编译器警告可能就足够了.但他们选择彻底禁止它,可能是因为阵列不再重要,因为我们现在拥有通用集合