對比Java的ArrayList與.net的List

來源:互聯網
上載者:User

今天看見一位園友寫了一篇非常詳細的文章《ArrayList源碼分析》,很佩服寫的如此仔細和詳細。

在看這篇文章時,我也和.net的List<T>做了對比,因為我非常熟悉List<T>的實現,就寫了此篇文章說明各自實現的差異。

  • 儲存
//Javaprivate transient Object[] elementData;

Java的此類雖然對外是泛型的,但內部卻不是使用泛型的數組儲存,沒有.net好;

//.netprivate T[] _items;
  • 預設構造
//Javapublic ArrayList() {this(10);

Java預設構建了大小為10的數組,事實上,很多的時候我們開始根本不儲存資料,而.net預設是0,而且使用一個靜態0數組執行個體,.net要聰明的多。

//.netpublic List(){    this._items = List<T>._emptyArray;}
  • 添加資料
//javapublic boolean add(E e) {    ensureCapacity(size + 1);  // Increments modCount!!    elementData[size++] = e;    return true;    }

顯然,無論數組是否大小夠用,java都會嘗試調用ensureCapacity方法,雖然此方法大多數並不會擴大數組(足夠空間),但這造成了多調用一次方法。.net在這一塊非常的小心。

//.netpublic void Add(T item){    if (this._size == this._items.Length)    {        this.EnsureCapacity(this._size + 1);    }    this._items[this._size++] = item;    this._version++;}

在擴充多大的問題上,大家的意見似乎不一致,

//Java     public void ensureCapacity(int minCapacity) {     modCount++;     int oldCapacity = elementData.length;     if (minCapacity > oldCapacity) {         Object oldData[] = elementData;         int newCapacity = (oldCapacity * 3)/2 + 1;             if (newCapacity < minCapacity)         newCapacity = minCapacity;             // minCapacity is usually close to size, so this is a win:             elementData = Arrays.copyOf(elementData, newCapacity);     }     }

Java使用奇怪的比例,增加2/3大小,而.net似乎很簡單,增加2倍,具體誰更科學,我還做不出判斷。

//.netprivate void EnsureCapacity(int min){    if (this._items.Length < min)    {        int num = (this._items.Length == 0) ? 4 : (this._items.Length * 2);        if (num > 2146435071)        {            num = 2146435071;        }        if (num < min)        {            num = min;        }        this.Capacity = num;    }}
  • 添加一批資料
//javapublic boolean addAll(int index, Collection<? extends E> c) {     if (index > size || index < 0)         throw new IndexOutOfBoundsException(         "Index: " + index + ", Size: " + size);      Object[] a = c.toArray();     int numNew = a.length;     ensureCapacity(size + numNew);  // Increments modCount      int numMoved = size - index;     if (numMoved > 0)         System.arraycopy(elementData, index, elementData, index + numNew,                  numMoved);          System.arraycopy(a, 0, elementData, index, numNew);     size += numNew;     return numNew != 0;     }

 

添加一批資料時,在擴充大小時,java首先做一次複製(toArray)到臨時數組,然後再複製到實際數組elementData。

//.netICollection<T> collection2 = collection as ICollection<T>;    if (collection2 != null)    {        int count = collection2.Count;        if (count > 0)        {            this.EnsureCapacity(this._size + count);            if (index < this._size)            {                Array.Copy(this._items, index, this._items, index + count, this._size - index);            }            if (this == collection2)            {                Array.Copy(this._items, 0, this._items, index, index);                Array.Copy(this._items, index + count, this._items, index * 2, this._size - index);            }            else            {                T[] array = new T[count];                collection2.CopyTo(array, 0);                array.CopyTo(this._items, index);            }            this._size += count;        }    }

.net 的代碼我看起來非常的奇怪,理論上,他可以調用collection2的copyto直接存入this._items的指定位置,這樣就減少了一次複製,但不知道為什麼他沒有這樣做。

  • 其他的不同

判斷項目相等,java用的是對象的相等方法,而.net用的是泛型版本的相等運算,效率更高。Clear時清除資料內容時使用for迴圈,而.net調用了Array的快速方法。

還有其他的不同嘛?我目前沒有找到,感覺大部分的時候差別不大,可能.net稍微細緻一些,你覺得呢?

 

 

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.