CodeGym /課程 /JAVA 25 SELF /Collection、List、Set、Map 介面:階層結構

Collection、List、Set、Map 介面:階層結構

JAVA 25 SELF
等級 27 , 課堂 0
開放

1. 什麼是 Collection 介面

在 Java 中,介面就像契約:如果類別實作介面,就必須提供該介面所有方法的實作。介面本身不保存狀態,也不包含程式碼(幾乎如此:自 Java 8 起允許有 default 方法,但此處重點在於基本概念)。

Collection 是 Java 中多數集合的基礎介面。它定義了集合能做的事:新增元素、刪除元素、取得大小、檢查是否包含元素等。

public interface Collection<E> extends Iterable<E> {
    int size();
    boolean isEmpty();
    boolean contains(Object o);
    boolean add(E e);
    boolean remove(Object o);
    void clear();
    Iterator<E> iterator();
    // ... 還有一堆實用的方法
}

關鍵方法:

  • add(E e) — 新增元素。
  • remove(Object o) — 刪除元素。
  • size() — 取得元素數量。
  • isEmpty() — 檢查集合是否為空。
  • contains(Object o) — 檢查是否包含某元素。
  • clear() — 清空集合。
  • iterator() — 取得可用於迭代的迭代器。

為什麼 Map 不繼承 Collection?

Map 在集合中是獨立的一支。因為 Map 是由「鍵 → 值」配對組成,而不是單純的元素集合。它有不同的契約與方法集合。比如在 Map 中沒有 add 方法,因為新增是透過 put(key, value) 完成;此外,不知道鍵時去檢查值是否存在也沒有意義。

2. 集合的階層結構

可以想像主要介面的「樹狀」結構如下:

                Iterable
                   |
               Collection
               /    |    \
            List   Set   Queue
                          |
                        Deque
  • Iterable — 最底層的介面:凡是能在 for-each 迴圈中迭代的東西。
  • Collection — 擴充自 Iterable,新增了對元素集合進行操作的方法。
  • 三大分支:
    • List — 有序列表,允許重複。
    • Set — 唯一元素的集合,順序取決於實作。
    • Queue — 佇列(通常是 FIFO);其子類為 Deque(雙端佇列)。

Map 是獨立的一支:

                Map
               /   \
         HashMap  TreeMap

階層可視化(示意圖)

                            +--------------------+
                            |     Iterable<E>    |
                            +--------------------+
                                     |
                            +--------------------+
                            |   Collection<E>    |
                            +--------------------+
                          /     |         \
                +--------+   +-------+   +-------+
                |  List  |   |  Set |   | Queue |
                +--------+   +-------+   +-------+
                                     |
                                  +------+
                                  |Deque |
                                  +------+

        +--------------------+
        |      Map<K,V>      |
        +--------------------+

3. List:有序且允許重複的集合

List 是一種集合,其特性為:

  • 元素的順序很重要(第一個、第二個、第三個…)。
  • 允許相同元素(可有重複)。
  • 可透過索引取得元素(如 list.get(2))、替換、或插入到任意位置。

實作範例: ArrayList — 以索引存取很快;LinkedList — 適合在中間頻繁插入/刪除的情境。

import java.util.*;

List<String> shoppingList = new ArrayList<>();
shoppingList.add("牛奶");
shoppingList.add("麵包");
shoppingList.add("起司");
shoppingList.add("麵包"); // 允許重複!

System.out.println(shoppingList.get(1)); // "麵包"

List 的常用方法:

  • add(E e)add(int index, E e)
  • get(int index)set(int index, E e)
  • remove(int index)remove(Object o)
  • indexOf(Object o)lastIndexOf(Object o)

4. Set:唯一元素的集合

Set 是一種集合,其特性為:

  • 每個元素皆唯一(不允許重複)。
  • HashSet 不保證順序,TreeSet 可排序,LinkedHashSet 保留插入順序。

實作範例: HashSetTreeSetLinkedHashSet

import java.util.*;

Set<String> uniqueNames = new HashSet<>();
uniqueNames.add("安雅");
uniqueNames.add("鮑里斯");
uniqueNames.add("安雅"); // 不會加入—已經存在!

System.out.println(uniqueNames.contains("安雅")); // true
System.out.println(uniqueNames.size()); // 2

Set 的常用方法:

  • add(E e)remove(Object o)
  • contains(Object o)
  • size()isEmpty()

5. Map:鍵值對的集合

Map 是一種集合,其特性為:

  • 每個元素都是一組鍵 → 值配對。
  • 鍵必須唯一,值可以重複。
  • 可透過鍵進行快速存取。

實作範例: HashMapTreeMapLinkedHashMap

import java.util.*;

Map<String, String> phoneBook = new HashMap<>();
phoneBook.put("安雅", "+19991112233");
phoneBook.put("鮑里斯", "+19994445566");
phoneBook.put("安雅", "+19990001122"); // 會覆寫安雅的號碼!

System.out.println(phoneBook.get("安雅")); // "+19990001122"
System.out.println(phoneBook.containsKey("鮑里斯")); // true

Map 的常用方法:

  • put(K key, V value)get(K key)
  • remove(K key)
  • containsKey(K key)containsValue(V value)
  • keySet()values()entrySet()

6. 階層可視化:一圖看懂

簡要匯總表:

介面 說明 實作範例 關鍵特性
List
有序清單
ArrayList, LinkedList
可依索引存取,允許重複
Set
唯一值的集合
HashSet, TreeSet
只允許唯一元素
Map
鍵值對
HashMap, TreeMap
鍵唯一,值可重複

階層示意:

                Collection
                /    |    \
             List   Set   Queue
                            |
                          Deque

                Map(獨立)

7. 何時使用哪個介面

List

  • 元素的順序很重要時(例如使用者操作歷史)。
  • 當需要重複元素時(例如訂單項目)。
  • 當需要快速依索引存取/替換時。

Set

  • 當需要唯一性時(email、登入名稱、id)。
  • 當不在意順序,或反過來—需要自動排序的集合(TreeSet)。

Map

  • 當需要對應鍵與值時(id → 物件,登入 → 個人檔案)。
  • 當需要以鍵快速查找時。
  • 當鍵必須唯一而值不必唯一時。

8. 使用集合階層的常見錯誤

錯誤 1:在變數宣告時使用了錯誤的介面。 如果你寫 ArrayList<String> list = new ArrayList<>();,就把自己綁死在某個實作上。更好的做法是 List<String> list = new ArrayList<>();——如此更容易替換實作。

錯誤 2:嘗試在 Set 中加入重複元素並期待它們會出現。 這不是 bug,而是設計特性:Set 依定義就不保存重複元素。重複插入會被忽略。

錯誤 3:把 Map 當成一般集合來用。 Map 既不是列表也不是集合。要遍歷時請使用 keySet()values()entrySet()

錯誤 4:在 HashSet 或 HashMap 中期待有順序。 HashSetHashMap 不保證順序。若順序很重要—請使用 LinkedHashSetLinkedHashMap

錯誤 5:為了唯一元素而使用 List。 若需要唯一性—請使用 SetList 不會避免重複。

留言
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION