集合轉數組:toArray()最優化方法探索

優化背景

  • 有些場景下(比如入參要求)需要將集合(比如List)轉為數組類型,利用集合的toArray方法應該最為方便的,對於toArray()無參方法其返回的是Object[],強制轉其他類型數組會ClassCastException。推薦使用帶參數的toArray(T[]),不過使用上需要注意

  • list強轉數組拋異常-ClassCastException

 @Test
    //list強轉數組拋異常-ClassCastException
    public void arrayError(){
        List<String> listToArray = new ArrayList<>();
        listToArray.add("jav");
        listToArray.add(0, "python");
        listToArray.add("php");
        listToArray.add("c#");
        String[] str = (String[]) listToArray.toArray();
        System.out.println(str);
    }

異常資訊列印:

java.lang.ClassCastException: [Ljava.lang.Object; cannot be cast to [Ljava.lang.String;

  • 對於toArray()無參方法其返回的是Object[],正確寫法
@Test
    //list轉數組,使用object對象接受再循環遍歷轉出
    public void arrayObject(){
        List<String> listToArray = new ArrayList<>();
        listToArray.add("jav");
        listToArray.add(0, "python");
        listToArray.add("php");
        listToArray.add("c#");
        String[] s = new String[listToArray.size()];
        Object[] o = listToArray.toArray();
        for (int i = 0; i < o.length; i++) {
            s[i] = o[i].toString();
        }
        System.out.println(Arrays.toString(s));
    }

輸出:[python, java, php, c#]

toArray(new String[0]), 創建一個大小為0的數組,當為輸入數組長度小於集合size時,toArray方法會自動創建一個等大數組放入數據並返回。
toArray(new String[100000]),同上輸入的10w數組比集合size小,toArray方法會重新創建一個等大數組放入數據並返回,原來的10w數組等於白建了
toArray(new String[1000000]),輸入數組長度與集合size相等,當是一個理想狀態時,即數組size沒有發生變化(比如沒有並發情況),那麼toArray方法會直接使用輸入數組並返回,但如果在輸入數組創建之後,原集合size發生了變化,最糟糕的情況會退化為#2
toArray(new String[2000000]),輸入數組長度大於集合size,那麼toArray方法會直接使用輸入數組並返回,當然多出去的那部分數組量就算浪費了

  • 最優化寫法
@Test
    //list轉數組-最優化寫法
    public void OptimizeCode(){
        List<String> listToArray = new ArrayList<>();
        listToArray.add("jav");
        listToArray.add(0, "python");
        listToArray.add("php");
        listToArray.add("c#");
        String[] str = listToArray.toArray(new String[0]);
        System.out.println(Arrays.toString(str));
    }

輸出:[python, java, php, c#]

  • 由此可以看出,如果在沒有特殊需要的情況下,使用#1是比較高效的,也是大多數情況下比較推薦的寫法