最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

java中ArrayList 、LinkList的區(qū)別分析

 更新時間:2013年05月07日 10:00:35   作者:  
java中ArrayList 、LinkList的區(qū)別分析,需要的朋友可以參考一下

1.ArrayList是實現(xiàn)了基于動態(tài)數(shù)組的數(shù)據(jù)結(jié)構(gòu),LinkedList基于鏈表的數(shù)據(jù)結(jié)構(gòu)。
     2.對于隨機訪問get和set,ArrayList優(yōu)于LinkedList,因為ArrayList可以隨機定位,而LinkedList要移動指針一步一步的移動到節(jié)點處。(參考數(shù)組與鏈表來思考)
     3.對于新增和刪除操作add和remove,LinedList比較占優(yōu)勢,只需要對指針進行修改即可,而ArrayList要移動數(shù)據(jù)來填補被刪除的對象的空間。

ArrayList和LinkedList是兩個集合類,用于存儲一系列的對象引用(references)。例如我們可以用ArrayList來存儲一系列的String或者Integer。那么ArrayList和LinkedList在性能上有什么差別呢?什么時候應該用ArrayList什么時候又該用LinkedList呢?

一.時間復雜度

首先一點關(guān)鍵的是,ArrayList的內(nèi)部實現(xiàn)是基于基礎的對象數(shù)組的,因此,它使用get方法訪問列表中的任意一個元素時(random-access),它的速度要比LinkedList快。LinkedList中的get方法是按照順序從列表的一端開始檢查,直到另外一端。對LinkedList而言,訪問列表中的某個指定元素沒有更快的方法了。

假設我們有一個很大的列表,它里面的元素已經(jīng)排好序了,這個列表可能是ArrayList類型的也可能是LinkedList類型的,現(xiàn)在我們對這個列表來進行二分查找(binary search),比較列表是ArrayList和LinkedList時的查詢速度,看下面的程序:

復制代碼 代碼如下:

package com.mangocity.test;
import java.util.LinkedList;
import java.util.List;
import java.util.Random;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
public class TestList ...{
     public static final int N=50000;
     public static List values;
     static...{
         Integer vals[]=new Integer[N];
         Random r=new Random();
         for(int i=0,currval=0;i<N;i++)...{
             vals=new Integer(currval);
             currval+=r.nextInt(100)+1;
         }
         values=Arrays.asList(vals);
     }
     static long timeList(List lst)...{
         long start=System.currentTimeMillis();
         for(int i=0;i<N;i++)...{
             int index=Collections.binarySearch(lst, values.get(i));
             if(index!=i)
                 System.out.println("***錯誤***");
         }
         return System.currentTimeMillis()-start;
     }
     public static void main(String args[])...{
         System.out.println("ArrayList消耗時間:"+timeList(new ArrayList(values)));
         System.out.println("LinkedList消耗時間:"+timeList(new LinkedList(values)));
     }
}

 我得到的輸出是:ArrayList消耗時間:15

                 LinkedList消耗時間:2596

這個結(jié)果不是固定的,但是基本上ArrayList的時間要明顯小于LinkedList的時間。因此在這種情況下不宜用LinkedList。二分查找法使用的隨機訪問(randomaccess)策略,而LinkedList是不支持快速的隨機訪問的。對一個LinkedList做隨機訪問所消耗的時間與這個list的大小是成比例的。而相應的,在ArrayList中進行隨機訪問所消耗的時間是固定的。

這是否表明ArrayList總是比LinkedList性能要好呢?這并不一定,在某些情況下LinkedList的表現(xiàn)要優(yōu)于ArrayList,有些算法在LinkedList中實現(xiàn)時效率更高。比方說,利用Collections.reverse方法對列表進行反轉(zhuǎn)時,其性能就要好些。

看這樣一個例子,假如我們有一個列表,要對其進行大量的插入和刪除操作,在這種情況下LinkedList就是一個較好的選擇。請看如下一個極端的例子,我們重復的在一個列表的開端插入一個元素:

復制代碼 代碼如下:

package com.mangocity.test;
import java.util.*;
public class ListDemo {
     static final int N=50000;
     static long timeList(List list){
     long start=System.currentTimeMillis();
     Object o = new Object();
     for(int i=0;i<N;i++)
         list.add(0, o);
     return System.currentTimeMillis()-start;
     }
     public static void main(String[] args) {
         System.out.println("ArrayList耗時:"+timeList(new ArrayList()));
         System.out.println("LinkedList耗時:"+timeList(new LinkedList()));
     }
}

  這時我的輸出結(jié)果是:ArrayList耗時:2463

                           LinkedList耗時:15

這和前面一個例子的結(jié)果截然相反,當一個元素被加到ArrayList的最開端時,所有已經(jīng)存在的元素都會后移,這就意味著數(shù)據(jù)移動和復制上的開銷。相反的,將一個元素加到LinkedList的最開端只是簡單的為這個元素分配一個記錄,然后調(diào)整兩個連接。在LinkedList的開端增加一個元素的開銷是固定的,而在ArrayList的開端增加一個元素的開銷是與ArrayList的大小成比例的。

二.空間復雜度

在LinkedList中有一個私有的內(nèi)部類,定義如下:

private static class Entry {
         Object element;
         Entry next;
         Entry previous;
     }

每個Entry對象reference列表中的一個元素,同時還有在LinkedList中它的上一個元素和下一個元素。一個有1000個元素的LinkedList對象將有1000個鏈接在一起的Entry對象,每個對象都對應于列表中的一個元素。這樣的話,在一個LinkedList結(jié)構(gòu)中將有一個很大的空間開銷,因為它要存儲這1000個Entity對象的相關(guān)信息。

ArrayList使用一個內(nèi)置的數(shù)組來存儲元素,這個數(shù)組的起始容量是10.當數(shù)組需要增長時,新的容量按如下公式獲得:新容量=(舊容量*3)/2+1,也就是說每一次容量大概會增長50%。這就意味著,如果你有一個包含大量元素的ArrayList對象,那么最終將有很大的空間會被浪費掉,這個浪費是由ArrayList的工作方式本身造成的。如果沒有足夠的空間來存放新的元素,數(shù)組將不得不被重新進行分配以便能夠增加新的元素。對數(shù)組進行重新分配,將會導致性能急劇下降。如果我們知道一個ArrayList將會有多少個元素,我們可以通過構(gòu)造方法來指定容量。我們還可以通過trimToSize方法在ArrayList分配完畢之后去掉浪費掉的空間。

三.總結(jié)

ArrayList和LinkedList在性能上各有優(yōu)缺點,都有各自所適用的地方,總的說來可以描述如下:

性能總結(jié):

- add()操作 delete()操作 insert操作 index取值操作 iterator取值操作
ArrayList/Vector/Stack 極優(yōu) 極優(yōu)
LinkedList 極優(yōu)

1.對ArrayList和LinkedList而言,在列表末尾增加一個元素所花的開銷都是固定的。對ArrayList而言,主要是在內(nèi)部數(shù)組中增加一項,指向所添加的元素,偶爾可能會導致對數(shù)組重新進行分配;而對LinkedList而言,這個開銷是統(tǒng)一的,分配一個內(nèi)部Entry對象。

2.在ArrayList的中間插入或刪除一個元素意味著這個列表中剩余的元素都會被移動;而在LinkedList的中間插入或刪除一個元素的開銷是固定的。

3.LinkedList不支持高效的隨機元素訪問。

4.ArrayList的空間浪費主要體現(xiàn)在在list列表的結(jié)尾預留一定的容量空間,而LinkedList的空間花費則體現(xiàn)在它的每一個元素都需要消耗相當?shù)目臻g

可以這樣說:當操作是在一列數(shù)據(jù)的后面添加數(shù)據(jù)而不是在前面或中間,并且需要隨機地訪問其中的元素時,使用ArrayList會提供比較好的性能;當你的操作是在一列數(shù)據(jù)的前面或中間添加或刪除數(shù)據(jù),并且按照順序訪問其中的元素時,就應該使用LinkedList了。

java中ArrayList 、List區(qū)別

List集合
    List繼承自Collection接口。List是一種有序集合,List中的元素可以根據(jù)索引(順序號:元素在集合中處于的位置信息)進行取得/刪除/插入操作。

    跟Set集合不同的是,List允許有重復元素。對于滿足e1.equals(e2)條件的e1與e2對象元素,可以同時存在于List集合中。當然,也有List的實現(xiàn)類不允許重復元素的存在。
   同時,List還提供一個listIterator()方法,返回一個ListIterator接口對象,和Iterator接口相比,ListIterator添加元素的添加,刪除,和設定等方法,還能向前或向后遍歷。

List跟Collection的關(guān)系:
java.util.Collection [I]
+--java.util.List [I]
   +--java.util.ArrayList [C]
   +--java.util.LinkedList [C]
   +--java.util.Vector [C]
      +--java.util.Stack [C]

List接口的實現(xiàn)類主要有ArrayList,LinkedList,Vector,Stack等。

父子關(guān)系.
   List是一個接口,ArrayList繼承與這個接口并實現(xiàn)了它.
   用的時候一般都用ArrayList.沒用過List. 可以這么用:List list = new ArrayList();

Collection接口
    Collection是最基本的集合接口,一個Collection代表一組Object,即Collection的元素(Elements)。一些Collection允許相同的元素而另一些不行。一些能排序而另一些不行。Java SDK不提供直接繼承自Collection的類,JavaSDK提供的類都是繼承自Collection的“子接口”如List和Set。
    所有實現(xiàn)Collection接口的類都必須提供兩個標準的構(gòu)造函數(shù):無參數(shù)的構(gòu)造函數(shù)用于創(chuàng)建一個空的Collection,有一個Collection參數(shù)的構(gòu)造函數(shù)用于創(chuàng)建一個新的Collection,這個新的Collection與傳入的Collection有相同的元素。后一個構(gòu)造函數(shù)允許用戶復制一個Collection。

     如何遍歷Collection中的每一個元素?不論Collection的實際類型如何,它都支持一個iterator()的方法,該方法返回一個迭代子,使用該迭代子即可逐一訪問Collection中每一個元素。典型的用法如下:
    Iterator it = collection.iterator(); // 獲得一個迭代子
    while(it.hasNext()) {
                             Object obj = it.next(); // 得到下一個元素
       }
由Collection接口派生的兩個接口是List和Set。

    List接口:
    List是有序的Collection,使用此接口能夠精確的控制每個元素插入的位置。用戶能夠使用索引(元素在List中的位置,類似于數(shù)組下標)來訪問List中的元素,這類似于Java的數(shù)組。
和下面要提到的Set不同,List允許有相同的元素。
除了具有Collection接口必備的iterator()方法外,List還提供一個listIterator()方法,返回一個ListIterator接口,和標準的Iterator接口相比,ListIterator多了一些add()之類的方法,允許添加,刪除,設定元素,還能向前或向后遍歷。
    實現(xiàn)List接口的常用類有LinkedList,ArrayList,Vector和Stack。

     LinkedList類
     LinkedList實現(xiàn)了List接口,允許null元素。此外LinkedList提供額外的get,remove,insert方法在LinkedList的首部或尾部。這些操作使LinkedList可被用作堆棧(stack),隊列(queue)或雙向隊列(deque)。
    注意LinkedList沒有同步方法。如果多個線程同時訪問一個List,則必須自己實現(xiàn)訪問同步。一種解決方法是在創(chuàng)建List時構(gòu)造一個同步的List:
List list = Collections.synchronizedList(new LinkedList(...));

ArrayList類
ArrayList實現(xiàn)了可變大小的數(shù)組。它允許所有元素,包括null。ArrayList沒有同步。
size,isEmpty,get,set方法運行時間為常數(shù)。但是add方法開銷為分攤的常數(shù),添加n個元素需要O(n)的時間。其他的方法運行時間為線性。
每個ArrayList實例都有一個容量(Capacity),即用于存儲元素的數(shù)組的大小。這個容量可隨著不斷添加新元素而自動增加,但是增長算法并沒有定義。當需要插入大量元素時,在插入前可以調(diào)用ensureCapacity方法來增加ArrayList的容量以提高插入效率。
和LinkedList一樣,ArrayList也是非同步的(unsynchronized)。

總結(jié)
  如果涉及到堆棧,隊列等操作,應該考慮用List,對于需要快速插入,刪除元素,應該使用LinkedList,如果需要快速隨機訪問元素,應該使用ArrayList。
      盡量返回接口而非實際的類型,如返回List而非ArrayList,這樣如果以后需要將ArrayList換成LinkedList時,客戶端代碼不用改變。這就是針對抽象編程。

相關(guān)文章

  • Java中的內(nèi)存泄露問題和解決辦法

    Java中的內(nèi)存泄露問題和解決辦法

    大家好,本篇文章主要講的是Java中的內(nèi)存泄露問題和解決辦法,感興趣的同學趕快來看一看吧,對你有幫助的話記得收藏一下
    2022-01-01
  • 你還在用Synchronized?Atomic你了解不?

    你還在用Synchronized?Atomic你了解不?

    這篇文章主要介紹了你還在用Synchronized?Atomic你了解不? 文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2018-12-12
  • Java使用非覆蓋的方法實現(xiàn)替換PDF中的文本

    Java使用非覆蓋的方法實現(xiàn)替換PDF中的文本

    這篇文章主要為大家詳細介紹了Java如何使用非覆蓋的方法實現(xiàn)替換PDF中的文本,文中的示例代碼講解詳細,感興趣的小伙伴可以跟隨小編一起學習一下
    2024-02-02
  • 淺談java中為什么實體類需要實現(xiàn)序列化

    淺談java中為什么實體類需要實現(xiàn)序列化

    下面小編就為大家?guī)硪黄獪\談java中為什么實體類需要實現(xiàn)序列化。小編覺得挺不錯的,現(xiàn)在就分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2017-05-05
  • Java?嵌入數(shù)據(jù)引擎從?SQLite?到?SPL詳解

    Java?嵌入數(shù)據(jù)引擎從?SQLite?到?SPL詳解

    這篇文章主要介紹了Java?嵌入數(shù)據(jù)引擎:從?SQLite?到?SPL,SQLite架構(gòu)簡單,其核心雖然是C語言開發(fā)的,但封裝得比較好,對外呈現(xiàn)為一個小巧的Jar包,能方便地集成在Java應用中,本文給大家介紹的非常詳細,需要的朋友參考下
    2022-07-07
  • java實現(xiàn)簡單音樂播放器

    java實現(xiàn)簡單音樂播放器

    這篇文章主要為大家詳細介紹了java實現(xiàn)簡單音樂播放器,文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2019-06-06
  • Jmeter非GUI模式運行分布式測試

    Jmeter非GUI模式運行分布式測試

    這篇文章主要介紹了Jmeter非GUI模式運行分布式測試,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友可以參考下
    2020-10-10
  • MyBatis-Plus實現(xiàn)連表查詢的方法實例

    MyBatis-Plus實現(xiàn)連表查詢的方法實例

    這篇文章主要給大家介紹了關(guān)于MyBatis-Plus實現(xiàn)連表查詢的相關(guān)資料,文中通過實例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友可以參考下
    2022-01-01
  • java?byte數(shù)組轉(zhuǎn)String的幾種常用方法

    java?byte數(shù)組轉(zhuǎn)String的幾種常用方法

    在Java中數(shù)組是一種非常常見的數(shù)據(jù)結(jié)構(gòu),它可以用來存儲多個相同類型的數(shù)據(jù),有時候,我們需要將數(shù)組轉(zhuǎn)換為字符串,以便于輸出或者傳遞給其他方法,這篇文章主要給大家介紹了關(guān)于java?byte數(shù)組轉(zhuǎn)String的幾種常用方法,需要的朋友可以參考下
    2024-09-09
  • Javaweb實現(xiàn)在線人數(shù)統(tǒng)計代碼實例

    Javaweb實現(xiàn)在線人數(shù)統(tǒng)計代碼實例

    這篇文章主要介紹了Javaweb實現(xiàn)在線人數(shù)統(tǒng)計代碼實例,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友可以參考下
    2019-11-11

最新評論

西乌| 镇雄县| 南京市| 文安县| 博兴县| 瓮安县| 宜昌市| 平潭县| 德江县| 灯塔市| 城口县| 土默特右旗| 长治市| 南雄市| 英吉沙县| 尉犁县| 公主岭市| 曲靖市| 曲沃县| 永昌县| 临汾市| 闸北区| 巴中市| 靖州| 穆棱市| 县级市| 麟游县| 五莲县| 重庆市| 大冶市| 青岛市| 常熟市| 融水| 三穗县| 南雄市| 建始县| 灌云县| 囊谦县| 驻马店市| 临湘市| 报价|