贏在執(zhí)行

          這個世界上只有兩樣?xùn)|西愈分享愈多,那就是智慧與愛。

          BlogJava 首頁 新隨筆 聯(lián)系 聚合 管理
            17 Posts :: 11 Stories :: 13 Comments :: 0 Trackbacks

          1 、什么是 ArrayList
          ????ArrayList 就是傳說中的動態(tài)數(shù)組,用 MSDN 中的說法,就是 Array 的復(fù)雜版本,它提供了如下一些好處:

          • 動態(tài)的增加和減少元素
          • 實現(xiàn)了 ICollection IList 接口
          • 靈活的設(shè)置數(shù)組的大小


          2 、如何使用 ArrayList
          ???? 最簡單的例子:
          ArrayList?List?=?new?ArrayList();
          for(?int?i=0;i<10;i++?)?//
          給數(shù)組增加 10 Int 元素
          List.Add(i);?
          //..
          程序做一些處理
          List.RemoveAt(5);//
          將第 6 個元素移除
          for(?int?i=0;i<3;i++?)?//
          再增加 3 個元素
          ? List.Add(i+20);
          Int32[]?values?=?(Int32[])List.ToArray(typeof(Int32));//
          返回 ArrayList 包含的數(shù)組

          這是一個簡單的例子,雖然沒有包含 ArrayList 所有的方法,但是可以反映出 ArrayList 最常用的用法

          3
          ArrayList 重要的方法和屬性
          1 )構(gòu)造器
          ????ArrayList
          提供了三個構(gòu)造器:
          public?ArrayList();
          默認(rèn)的構(gòu)造器,將會以默認(rèn)( 16 )的大小來初始化內(nèi)部的數(shù)組
          public?ArrayList(ICollection);
          用一個 ICollection 對象來構(gòu)造,并將該集合的元素添加到 ArrayList
          public?ArrayList(int);
          用指定的大小來初始化內(nèi)部的數(shù)組

          2 IsSynchronized 屬性和 ArrayList.Synchronized 方法
          ????IsSynchronized
          屬性指示當(dāng)前的 ArrayList 實例是否支持線程同步,而 ArrayList.Synchronized 靜態(tài)方法則會返回一個 ArrayList 的線程同步的封裝。
          ???? 如果使用非線程同步的實例,那么在多線程訪問的時候,需要自己手動調(diào)用 lock 來保持線程同步,例如:
          ArrayList?list?=?new?ArrayList();
          //...
          lock(?list.SyncRoot?)?//
          當(dāng) ArrayList 為非線程包裝的時候, SyncRoot 屬性其實就是它自己,但是為了滿足 ICollection SyncRoot 定義,這里還是使用 SyncRoot 來保持源代碼的規(guī)范性
          {
          list.Add(?
          Add?a?Item ?);
          }

          ?????
          如果使用 ArrayList.Synchronized 方法返回的實例,那么就不用考慮線程同步的問題,這個實例本身就是線程安全的,實際上 ArrayList 內(nèi)部實現(xiàn)了一個保證線程同步的內(nèi)部類, ArrayList.Synchronized 返回的就是這個類的實例,它里面的每個屬性都是用了 lock 關(guān)鍵字來保證線程同步。

          ****

          但是,使用這個方法( ArrayList.Synchronized )并不能保證枚舉的同步,例如,一個線程正在刪除或添加集合項,而另一個線程同時進行枚舉,這時枚舉將會拋出異常。所以,在枚舉的時候,你必須明確使用 SyncRoot 鎖定這個集合。

          ?

          Hashtable ArrayList 關(guān)于線程安全性的使用方法類似。

          ****

          3 Count 屬性和 Capacity 屬性
          ????Count
          屬性是目前 ArrayList 包含的元素的數(shù)量,這個屬性是只讀的。
          Capacity
          屬性是目前 ArrayList 能夠包含的最大數(shù)量,可以手動的設(shè)置這個屬性,但是當(dāng)設(shè)置為小于 Count 值的時候會引發(fā)一個異常。

          4 Add AddRange Remove RemoveAt RemoveRange Insert InsertRange
          ????
          這幾個方法比較類似
          Add
          方法用于添加一個元素到當(dāng)前列表的末尾
          AddRange
          方法用于添加一批元素到當(dāng)前列表的末尾
          Remove
          方法用于刪除一個元素,通過元素本身的引用來刪除
          RemoveAt
          方法用于刪除一個元素,通過索引值來刪除
          RemoveRange
          用于刪除一批元素,通過指定開始的索引和刪除的數(shù)量來刪除
          Insert
          用于添加一個元素到指定位置,列表后面的元素依次往后移動
          InsertRange
          用于從指定位置開始添加一批元素,列表后面的元素依次往后移動

          ????
          另外,還有幾個類似的方法:
          Clear
          方法用于清除現(xiàn)有所有的元素
          Contains
          方法用來查找某個對象在不在列表之中

          ????
          其他的我就不一一累贅了,大家可以查看 MSDN ,上面講的更仔細(xì)
          5 TrimSize 方法
          ????
          這個方法用于將 ArrayList 固定到實際元素的大小,當(dāng)動態(tài)數(shù)組元素確定不在添加的時候,可以調(diào)用這個方法來釋放空余的內(nèi)存。
          6 ToArray 方法
          ????
          這個方法把 ArrayList 的元素 Copy 到一個新的數(shù)組中。


          4
          ArrayList 與數(shù)組轉(zhuǎn)換
          ???? 1
          ArrayList?List?=?new?ArrayList();
          List.Add(1);
          List.Add(2);
          List.Add(3);

          Int32[]?values?=?(Int32[])List.ToArray(typeof(Int32));

          ????
          2
          ArrayList?List?=?new?ArrayList();
          List.Add(1);
          List.Add(2);
          List.Add(3);

          Int32[]?values?=?new?Int32[List.Count];
          List.CopyTo(values);

          ????
          上面介紹了兩種從 ArrayList 轉(zhuǎn)換到數(shù)組的方法

          ????
          3
          ArrayList?List?=?new?ArrayList();
          List.Add(?
          string ?);
          List.Add(?1?);
          //
          往數(shù)組中添加不同類型的元素

          object[]?values?=?List.ToArray(typeof(object)); //
          正確
          string[]?values?=?(string[])List.ToArray(typeof(string));?//
          錯誤

          和數(shù)組不一樣,因為可以轉(zhuǎn)換為 Object 數(shù)組,所以往 ArrayList 里面添加不同類型的元素是不會出錯的,但是當(dāng)調(diào)用 ArrayList 方法的時候,要么傳遞所有元素都可以正確轉(zhuǎn)型的類型或者 Object 類型,否則將會拋出無法轉(zhuǎn)型的異常。


          5
          ArrayList 最佳使用建議
          ???? 這一節(jié)我們來討論 ArrayList 與數(shù)組的差別,以及 ArrayList 的效率問題
          ??
          1 ArrayList Array 的復(fù)雜版本
          ArrayList
          內(nèi)部封裝了一個 Object 類型的數(shù)組,從一般的意義來說,它和數(shù)組沒有本質(zhì)的差別,甚至于 ArrayList 的許多方法,如 Index IndexOf Contains Sort 等都是在內(nèi)部數(shù)組的基礎(chǔ)上直接調(diào)用 Array 的對應(yīng)方法。
          ??
          2 )內(nèi)部的 Object 類型的影響
          ?????????
          對于一般的引用類型來說,這部分的影響不是很大,但是對于值類型來說,往 ArrayList 里面添加和修改元素,都會引起裝箱和拆箱的操作,頻繁的操作可能會影響一部分效率。
          但是恰恰對于大多數(shù)人,多數(shù)的應(yīng)用都是使用值類型的數(shù)組。
          消除這個影響是沒有辦法的,除非你不用它,否則就要承擔(dān)一部分的效率損失,不過這部分的損失不會很大。
          ??
          3 )數(shù)組擴容
          這是對 ArrayList 效率影響比較大的一個因素。
          每當(dāng)執(zhí)行 Add AddRange Insert InsertRange 等添加元素的方法,都會檢查內(nèi)部數(shù)組的容量是否不夠了,如果是,它就會以當(dāng)前容量的兩倍來重新構(gòu)建一個數(shù)組,將舊元素 Copy 到新數(shù)組中,然后丟棄舊數(shù)組,在這個臨界點的擴容操作,應(yīng)該來說是比較影響效率的。
          ?????
          1 :比如,一個可能有 200 個元素的數(shù)據(jù)動態(tài)添加到一個以默認(rèn) 16 個元素大小創(chuàng)建的 ArrayList 中,將會經(jīng)過:
          16*2*2*2*2?=?256
          四次的擴容才會滿足最終的要求,那么如果一開始就以:
          ArrayList?List?=?new?ArrayList(?210?);
          的方式創(chuàng)建 ArrayList ,不僅會減少 4 次數(shù)組創(chuàng)建和 Copy 的操作,還會減少內(nèi)存使用。

          ?????
          2 :預(yù)計有 30 個元素而創(chuàng)建了一個 ArrayList
          ArrayList?List?=?new?ArrayList(30);
          在執(zhí)行過程中,加入了 31 個元素,那么數(shù)組會擴充到 60 個元素的大小,而這時候不會有新的元素再增加進來,而且有沒有調(diào)用 TrimSize 方法,那么就有 1 次擴容的操作,并且浪費了 29 個元素大小的空間。如果這時候,用:
          ArrayList?List?=?new?ArrayList(40);
          那么一切都解決了。
          所以說,正確的預(yù)估可能的元素,并且在適當(dāng)?shù)臅r候調(diào)用 TrimSize 方法是提高 ArrayList 使用效率的重要途徑。
          ???
          4 )頻繁的調(diào)用 IndexOf Contains 等方法( Sort BinarySearch 等方法經(jīng)過優(yōu)化,不在此列)引起的效率損失
          首先,我們要明確一點, ArrayList 是動態(tài)數(shù)組,它不包括通過 Key 或者 Value 快速訪問的算法,所以實際上調(diào)用 IndexOf Contains 等方法是執(zhí)行的簡單的循環(huán)來查找元素,所以頻繁的調(diào)用此類方法并不比你自己寫循環(huán)并且稍作優(yōu)化來的快,如果有這方面的要求,建議使用 Hashtable SortedList 等鍵值對的集合。
          ArrayList?al=new?ArrayList();

          al.Add("How");
          al.Add("are");
          al.Add("you!");

          al.Add(100);
          al.Add(200);
          al.Add(300);

          al.Add(1.2);
          al.Add(22.8);

          .........

          //
          第一種遍歷 ?ArrayList? 對象的方法
          foreach(object?o?in?al)
          {
          Console.Write(o.ToString()+"?");
          }

          //
          第二種遍歷 ?ArrayList? 對象的方法
          IEnumerator?ie=al.GetEnumerator();
          while(ie.MoveNext())
          {
          Console.Write(ie.Curret.ToString()+"?");
          }

          //
          第三種遍歷 ?ArrayList? 對象的方法
          我忘記了 , 好象是 ? 利用 ?ArrayList 對象的一個屬性 , 它返回一此對象中的元素個數(shù) .

          然后在利用索引 ?
          for(int?i=0;i<Count;i++)
          {
          Console.Write(al[i].ToString()+"?");
          }
          ?

          posted on 2007-03-16 00:28 飛雪(leo) 閱讀(571) 評論(0)  編輯  收藏 所屬分類: JAVA基礎(chǔ)專區(qū)

          只有注冊用戶登錄后才能發(fā)表評論。


          網(wǎng)站導(dǎo)航:
           
          主站蜘蛛池模板: 荃湾区| 加查县| 灵石县| 宾川县| 南雄市| 商水县| 六盘水市| 颍上县| 芜湖市| 贵南县| 寻乌县| 和田县| 泗阳县| 康乐县| 顺平县| 宁德市| 安丘市| 隆安县| 宁陵县| 徐闻县| 郓城县| 巫溪县| 衡山县| 小金县| 宁乡县| 潮州市| 临沂市| 新野县| 涿州市| 梓潼县| 青州市| 阿拉尔市| 平塘县| 锡林浩特市| 两当县| 宁都县| 尖扎县| 司法| 峨眉山市| 彭水| 南昌市|