java Arraylist.addAll方法---arraycopy

問題是這樣產生的,網上一哥們發了一個面試題:

ListA 裏面有  1   2    3 


ListB裏面有  4    5   6 


讓ListA變成  1  2  3  4  5  6 

我覺得很簡單 ,就說用for循環遍歷 添加就好了。結果面試官說

答案是使用addAll方法,因爲這樣效率高:

我表示很費解,於是查閱了資料。

得出以下結論:

在小數據量時,for循環效率高,大數據量時addAll方法效率高:

原因如下:

ArrayList的addAll的實現爲:

public   boolean   addAll(Collection   c)   { 
                         Object[]   a   =   c.toArray(); 
                         int   numNew   =   a.length; 
ensureCapacity(size   +   numNew);      //   Increments   modCount 
                         System.arraycopy(a,   0,   elementData,   size,   numNew); 
                         size   +=   numNew; 
return   numNew   !=   0; 
             } 

 

很顯然。。在拷貝數組時使用了


arraycopy 這個方法。這個方法是使用拷貝內存的做法 ,效率比遍歷數組塊很多。

首先找到數據源 然後將該段內存拷貝。

 

當然值得注意的是,這個函數中還使用了toArray方法,這個方法是 要遍歷操作的

 

但是如果需要多次遍歷,那麼addAll還是在性能上會獲取優勢的. .

下面是網上的一個測試 在20組數據時 還是 for效率高,但是在大數據量的時候 arraycopy 方法就明顯佔優勢了。
http://www.exam8.com/computer/djks/dj2/Java/ziliao/200810/1314435.htmlhttp://www.exam8.com/computer/djks/dj2/Java/ziliao/200810/1314435.html

另外:

arraycopy的定義是這樣的

public static native void arraycopy(Object src,  int  srcPos, Object dest, int destPos,int length);

 

native關鍵字的意思是 這個函數的源碼在JDK中沒有的。但是他調用的是本地計算機中的函數

這個函數是C,或者C++寫完的,編譯成DLL。 java調用。所以效率比for循環要塊。

 

綜上所述 :爲什麼在大數據量時使用addall方法效率快?

1.使用內存拷貝,移動數據。

2.本地函數,執行效率高。

那小數據量時呢?

以上2點都不明顯,並且首先要調用toArray方法,在小數據量時,效果沒有for來的好。

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章