为了账号安全,请及时绑定邮箱和手机立即绑定

Java 集合 ArrayList、LinkedList 转换异常

Java 集合 ArrayList、LinkedList 转换异常

心有法竹 2021-12-01 19:48:18
我发现了一个奇怪的案例,到目前为止我无法解释。 public static void main(String[] args) {    LinkedList<Integer> a = new LinkedList<>();    a.add(2);    a.add(3);    a.add(4);    for (ArrayList ax : getBatches(a)){        System.out.println(ax);    }}private static ArrayList<ArrayList<Integer>> getBatches(List<Integer> optionIds) {        return new ArrayList(Arrays.asList(optionIds));}执行的结果是:线程“main”中的异常 java.lang.ClassCastException:java.util.LinkedList 不能转换为 java.util.ArrayList在 for 循环中出现异常。问题是:如何?返回类型为 ArrayList< ArrayList< Integer>> 的方法如何返回 LinkedList?
查看完整描述

3 回答

?
阿晨1998

TA贡献2037条经验 获得超6个赞

您的方法返回一个 raw ArrayList,这就是编译器允许它的原因。但是,在运行时,会尝试将 a LinkedList(您传递给getBatches方法的实例)强制转换为ArrayList,从而导致ClassCastException.


如果您将方法更改为:


private static ArrayList<ArrayList<Integer>> getBatches(List<Integer> optionIds) {

    return new ArrayList<>(Arrays.asList(optionIds));

}

你会得到一个编译错误。


为了避免编译和运行时错误,您需要将List传递给您的方法的 转换为ArrayList:


private static ArrayList<ArrayList<Integer>> getBatches(List<Integer> optionIds) {

    return new ArrayList<>(Arrays.asList(new ArrayList<>(optionIds)));

}

这将返回一个 ,ArrayList其单个元素是ArrayList包含与List传递给方法的元素相同的元素。


查看完整回答
反对 回复 2021-12-01
?
紫衣仙女

TA贡献1839条经验 获得超15个赞

getBatches()正在返回一个具有泛型类型的 ArrayList ArrayList<Integer>。的返回类型Arrays.asList()是一个List接口。为了从 List 到 ArrayList 它进行了隐式转换。问题在于您不能直接将 ArrayList 转换为 LinkedList。

解决这个问题相对简单。不是遍历ArrayLists,而是遍历Listseg for(List l: getBatches(a)。然后就getBatches()返回ArrayList<List<Integer>>

通常,您会希望尽可能使用最抽象的东西。如果您不需要实现特定的细节,ArrayList只需将其称为列表。


查看完整回答
反对 回复 2021-12-01
?
BIG阳

TA贡献1859条经验 获得超6个赞

这是使用原始类型的结果。

通过调用new ArrayList(...)无specifing泛型参数TArrayList<T>您正在使用的原始类型ArrayList

上面链接的文档说:

但是,如果将原始类型分配给参数化类型,则会收到警告:

Eclipse 显示以下与以下相关的警告new ArrayList(Arrays.asList(optionIds));

类型安全:类型的表达ArrayList需要未经检查的转换以符合ArrayList<ArrayList<Integer>>

因此,返回原始类型ArrayListArrayList<ArrayList<Integer>>.

的结果getBatches(a)是 类型ArrayList<ArrayList<Integer>>。此类型列表的元素类型为ArrayList<Integer>。将它们分配给ax使用原始类型ArrayList也没有编译时错误。

为了向后兼容,允许将参数化类型分配给它的原始类型:

但在运行时,当涉及到的元素的投getBatches(a)ArrayList无视该警告导致ClassCastException,因为运行时类型LinkedList不能被强制转换为ArrayList(此时已经与擦除泛型类型)。


查看完整回答
反对 回复 2021-12-01
  • 3 回答
  • 0 关注
  • 261 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信