簡體   English   中英

Java Collections ArrayList,LinkedList強制轉換異常

[英]Java Collections ArrayList, LinkedList cast Exception

我找到了一個奇怪的案例,到目前為止我無法解釋。

 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?

您的方法返回原始ArrayList ,這就是編譯器允許的原因。 但是,在運行時期間,會嘗試將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相同的元素。

getBatches()返回一個具有泛型類型ArrayList<Integer> Arrays.asList()的返回類型是List接口。 為了從List到ArrayList,它正在進行隱式轉換。 這個問題是你無法直接將ArrayList強制轉換為LinkedList。

解決這個問題相對簡單。 而不是遍歷ArrayList ,迭代List seg for(List l: getBatches(a) 。然后只需使getBatches()返回ArrayList<List<Integer>>

一般來說,你會想要使用最抽象的東西。 如果您不需要實現ArrayList特定細節,只需將其稱為List。

這是使用原始類型的結果。

通過調用new ArrayList(...)而不指定ArrayList<T>的泛型參數T ,您將使用原始類型ArrayList

上述鏈接文檔說:

但是,如果將原始類型分配給參數化類型,則會收到警告:

Eclipse顯示以下與new ArrayList(Arrays.asList(optionIds));相關的警告new ArrayList(Arrays.asList(optionIds));

類型安全: ArrayList類型的表達式需要未經檢查的轉換以符合ArrayList<ArrayList<Integer>>

因此,將原始類型的ArrayList作為ArrayList<ArrayList<Integer>>返回時不會導致編譯時錯誤。

getBatches(a)的結果是ArrayList<ArrayList<Integer>> 此類型列表的元素的類型為ArrayList<Integer> 使用原始類型ArrayList將它們分配給ax也不是編譯時錯誤。

為了向后兼容,允許將參數化類型分配給其原始類型:

但是在運行時,將getBatches(a)的元素getBatches(a)ArrayList忽略ClassCastException的警告結果,因為運行時類型LinkedList無法轉換為ArrayList (此時已經使用已擦除的泛型類型) 。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM