1. 程式人生 > >Java中的集合框架-Map

Java中的集合框架-Map

  前兩篇《Java中的集合框架-Commection(一)》《Java中的集合框架-Commection(二)》把集合框架中的Collection開發常用知識點作了一下記錄,從本篇開始,對集合框架裡的另外一部分Map作一下記錄。

一,集合框架的Map介面

  Map與Collection不同之處在於它是以鍵值對來儲存資料;

  Map比較常用的實現類有四個:HashTable,HashMap,LinkedHashMap,TreeMap;

  Map的方法也可以分為四類,增刪改查,大致如下:

  新增的方法:

      put(k,v)  此方法將一對Key:Value形式的資料新增到容器中,並返回此Key所對應的舊值的結果(如果Key已存在的話),若此Key是一個新的Key則返回一個null

      put(Map)  此方法的作用是把一個Map中的元素複製到此Map中

  刪除的方法:

      clear()  清除容器中的所有元素

      remove()  此方法移除一對Key:Value,返回的是被移除的鍵所對應的值

  修改的方法:

      put(k,v)  鍵相同,值不同便起到了修改的作用

  查詢的方法:

      containsKey(key)  是否包含指定的Key,若包含則返回true

      containsValue(value)  是否包含指定的Value,若包含則返回true

      get(key)  返回指定的鍵所對應的值

      isEmpty()  查詢Map是不是為空,若為空則返回true

      size()  返回Map中Key:Value的數量

      keySet()  返回Map中所有Key所組成的一個Set集合

      values()  返回Map中所有Value對應的Collection集合

      entrySet()  返回鍵值對所對應的Map.entry的Set集合

  其它的equals方法,hashcode方法便不再羅列。方法的使用還是到它的實現類中去演示,在此不作演示。

二,HashTable與HashMap

  HashTable是1.0出現的,後來它被HashSet所取代;

  HashTable內部結構是雜湊表,它是執行緒安全的,另外HashTable不可儲存null鍵以及null值;

  HashMap功能與HashTable基本相同,只是它非執行緒安全,另外它可儲存null健以及null值;

  雖然HashMap內部是雜湊表的結構,但是它真正的儲存結構是陣列+連結串列的形式,當一個元素被put進來的時候,它會先計算該元素的hashcode,當hashcode衝突的時候,它會使用連結串列進行掛載;

  當HashMap儲存null鍵和null值的時候,它會儲存到陣列下標0的位置,若該位置有元素存在則進行掛載。

  HashMap在儲存自定義物件的時候和HashSet一樣(其實HashSet裡面維護的就是一個HashMap),也會先呼叫該元素的hashcode方法,當hashcode相同是再去呼叫該元素的equals方法去判斷兩個元素是否為同一個元素,若是同一個元素則修改其原來的值為新值並返回原來的值;若元素的hashcode不同,則直接判斷為不同的元素進行儲存;演示如下:

 1 public class Person {
 2     private String name;
 3     private int age;
 4 
 5     public Person(String name, int age) {
 6         this.name = name;
 7         this.age = age;
 8     }
 9 
10     public String getName() {
11         return name;
12     }
13 
14     public void setName(String name) {
15         this.name = name;
16     }
17 
18     public int getAge() {
19         return age;
20     }
21 
22     public void setAge(int age) {
23         this.age = age;
24     }
25 
26 }
  主程式:
1     private static void fun_demo2() {
2         HashMap hm = new HashMap();
3         hm.put(new Person("張三", 32), "程式設計師");
4         hm.put(new Person("張三", 12), "專案經理");
5         hm.put(new Person("王五", 22), "老闆");
6         System.out.println(hm);
7     }

   程式執行結果:

        

  可見三個元素都被儲存進去了,這個原因很好理解,每new出來一個Person,它的hashcode是不一樣的,所以儲存了三個元素。下面我們改一下Person類,重寫一下hashcode和equals方法

 1 public class Person {
 2     private String name;
 3     private int age;
 4 
 5     public Person(String name, int age) {
 6         this.name = name;
 7         this.age = age;
 8     }
 9 
10     public String getName() {
11         return name;
12     }
13 
14     public void setName(String name) {
15         this.name = name;
16     }
17 
18     public int getAge() {
19         return age;
20     }
21 
22     public void setAge(int age) {
23         this.age = age;
24     }
25 
26     @Override
27     public int hashCode() {
28         return this.getName().hashCode();
29     }
30 
31     @Override
32     public boolean equals(Object obj) {
33         return true;
34     }
35 
36 }

  程式執行結果:

        

  可見我們把hashcode直接返回Person的name的hashcode,由於Person物件有兩個叫張三的,所以它會呼叫equals方法再進一步比較這兩個物件是否為同一個元素,我們的equals方法又返回了true,它就認定這兩個元素是同一個元素,所以拿第二個“張三”的Value值“專案經理”把第一個“張三”的Value值“程式設計師”給覆蓋掉了。

  其它的關於HashMap的方法不再一一演示。

三,LinkedHashMap

  LinkedHashMap與HashMap的區別是LinkedHashMap內部維護著一個所有元素的雙向連結串列,它能保證儲存進容器的元素與取出元素的順序一致;請看以下操作:

 1     private static void fun_demo3() {
 2         HashMap lhm = new HashMap();
 3         lhm.put(2, "z");
 4         lhm.put(3, "a");
 5         lhm.put(1, "b");
 6         lhm.put(0, "z");
 7         lhm.put(null, "t");
 8         Iterator iterator = lhm.entrySet().iterator();
 9         while (iterator.hasNext()) {
10             Map.Entry entry = (Entry) iterator.next();
11             System.out.println(entry.getKey() + ":" + entry.getValue());
12         }
13     }

   程式執行結果:

        

  它對元素的Key進行了自然順序的排序,之所以null元素在0元素的後面,就是因為null元素會自動儲存到陣列0的位置,若0的位置有了元素便進行鏈式儲存進行掛載;

  我們把上面的程式的第一行改為LinkedHashMap lhm=new LinkedHashMap();則程式執行結果如下:

        
  可見和我們儲存元素的位置是一樣的。

四,TreeMap

  TreeMap是基於二叉樹的結構來儲存資料的,它會按照鍵的自然順序進行儲存資料;

  當TreeMap儲存自定義物件時,此物件需要實現Comparable介面並重寫compareTo方法;

  也可接收一個Comparator比較器物件來例項化TreeMap;

  其操作方法與TreeSet相類似,便不再演示了(TreeSet內部便是TreeMap);