Java:集合,Map接口框架圖


Java集合大致可分為Set、List和Map三種體系,其中Set代表無序、不可重復的集合;List代表有序、重復的集合;而Map則代表具有映射關系的集合。Java 5之后,增加了Queue體系集合,代表一種隊列集合實現。

Java集合框架主要由Collection和Map兩個根接口及其子接口、實現類組成。本文僅探討Map接口及其子接口、實現類。

目錄

1. Map接口繼承樹
2. Map接口的基本操作
3. Map的遍歷
4. HashMap類和Hashtable類
  4.1 Properties類
  4.2 LinkedHashMap類
5. SortedMap接口及其TreeMap實現類
6. IdentityHashMap類
7. EnumMap類
8. 各種Map實現類選擇策略 

1. Map接口繼承樹

2. Map接口的基本操作:

  • V put(K key, V value): 將指定的值與此映射中的指定鍵相關聯(可選操作)。如果此映射中以前包含一個該鍵的映射關系,則用指定值替換舊值。
  • boolean containsKey(Object key): 如果此映射包含指定鍵的映射關系,則返回 true
  • boolean containsValue(Object value): 如果此映射為指定值映射一個或多個鍵,則返回 true
  • Set<Map.Entry<K,V>> entrySet(): 返回此映射中包含的映射關系的 set 視圖。
  • V get(Object key): 返回指定key對應的value
  • V remove(Object key): 刪除指定key對應的key-value對

3. Map的遍歷可以使用Iterator接口或者是foreach循環來實現

 參考:Java:集合,數組(Array)、集合(List/Set/Queue)、映射(Map)等的遍歷,比如:ArrayList,LinkedList,HashSet,HashMap

4. HashMap類和Hashtable類

  • Hashtable是線程安全的,而HashMap不是線程安全的。
  • Hashtable不允許null作為key和value,而HashMap則可以使用null作為key和value。

不建議使用Hashtable類,它是一個很古老的類,從JDK1.0開始。如果要考慮線程安全,建議使用Collections工具類將HashMap轉換為線程安全的。

4.1 Properties類

Properties類從Hashtable類繼承而來。額外方法主要有:

  • void load(InputStream inStream): 從屬性文件加載key-value對
  • void store(OutputStream out, String comments): 將當前的所有key-value對輸出到指定屬性文件
  • String getProperty(String key): 獲取指定key對應的value值
  • String getProperty(String key, String defaultValue): 用指定的鍵在屬性列表中搜索屬性。如果在屬性列表中未找到該鍵,則接着遞歸檢查默認屬性列表及其默認值。如果未找到屬性,則此方法返回默認值變量。
  • Object setProperty(String key, String value): 調用 Hashtable 的方法 put。使用 getProperty 方法提供並行性。

Properties還可以把key-value對以XML文件的格式保存,也可以從XML文件中加載。loadFromXML(InputStream in)及storeToXML(OutputStream os, String comment)。

4.2 LinkedHashMap類

LinkedHashMap從HashMap類繼承而來。以鏈表來維護內部順序。很多方面跟LinkedHashSet類似。LinkedHashMap它可以記住key-value對的添加時的順序, 同時避免使用TreeMap時性能受到的影響。

5. SortedMap接口及其TreeMap實現類

類似於SortedSet及TreeSet,TreeMap也可以自定義比較器(Comparable)實現定制排序。它的額外提供的方法也與TreeSet類似,增加了訪問第一個、前一個、后一個、最后一個key-value對的方法,並提供了從TreeMap中提取子集的方法。TreeMap不允許null作為key,要不然怎么比較呢?

  • firstEntry()/firstKey()/lastEntry()/lastKey()/higerEntry()/higerKey()/....../subMap(Object fromKey, Object toKey)/...

6. IdentityHashMap類

與HashMap的不同在於,只有兩個key嚴格相等(key1 == key2)時,IdentityHashMap才認為兩個key相等;而對於普通HashMap而言,只要key1.equals(key2)且hashCode相同即可。同樣允許null值,不能保證順序。

7. EnumMap類

EnumMap是一個與枚舉類一起使用的Map實現。它的key必須是單個枚舉類的枚舉值。EnumMap不允許使用null作為key,但可作為value。《Effective Java》第33條,用EnumMap代替序數索引,一個稍復雜的應用:

// Using a nested EnumMap to associate data with enum pairs - Pags 163-164
import java.util.*;

public enum Phase {
   SOLID, LIQUID, GAS;

   public enum Transition {
      MELT(SOLID, LIQUID), FREEZE(LIQUID, SOLID),
      BOIL(LIQUID, GAS),   CONDENSE(GAS, LIQUID),
      SUBLIME(SOLID, GAS), DEPOSIT(GAS, SOLID);

      private final Phase src;
      private final Phase dst;
        
      Transition(Phase src, Phase dst) {
         this.src = src;
         this.dst = dst;
      }
      // Initialize the phase transition map
      private static final Map<Phase, Map<Phase,Transition>> m =
        new EnumMap<Phase, Map<Phase,Transition>>(Phase.class);
      static {
         for (Phase p : Phase.values())
           m.put(p,new EnumMap<Phase,Transition>(Phase.class));
         for (Transition trans : Transition.values())
           m.get(trans.src).put(trans.dst, trans);
      }

      public static Transition from(Phase src, Phase dst) {
         return m.get(src).get(dst);
      }
   }

   // Simple demo program - prints a sloppy table
   public static void main(String[] args) {
       for (Phase src : Phase.values())
           for (Phase dst : Phase.values())
               if (src != dst)
                   System.out.printf("%s to %s : %s %n", src, dst,
                                     Transition.from(src, dst));
   }
}

8. 各種Map實現類選擇策略

  1. 正常情況使用HashMap,而不是Hashtable。
  2. 如果考慮排序,那么考慮使用TreeMap。通常TreeMap比HashMap等在插入、刪除操作時要慢不少,因為它需要在底層采用紅黑樹來管理key-value對。
  3. 如果考慮插入時的順序,那么使用LinkedHashMap是個不錯的選擇。
  4. 如果想優化垃圾回收,建議使用WeakHashMap實現類(本文未提及);要求key完全匹配(同一對象),則使用IdentityHashMap;還有枚舉類不多說了。
  5. 關於null值:Hashtable不允許key為null,也不允許value為null;TreeMap與EnumMap不允許key為null;HashMap及其子類LinkedHashMap,IdentityHashMap允許key為null。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM