集合體系速覽
Collection
├── List (有序、可重複) → ArrayList, LinkedList, Vector
├── Set (無序、不可重複) → HashSet, LinkedHashSet, TreeSet
└── Queue (隊列) → PriorityQueue, ArrayDeque
Map (鍵值對、Key無序不可重複) → HashMap, LinkedHashMap, TreeMap, Hashtable
一、List 接口詳解
1. 實例化
List<Course> list = new ArrayList<>(); // 推薦面向接口編程
2. 增
| 方法 | 說明 |
add(E e) | 尾部添加 |
add(int index, E e) | 指定位置插入 |
addAll(Collection<? extends E> c) | 批量添加到尾部 |
addAll(int index, Collection<? extends E> c) | 批量插入指定位置 |
// 數組轉 List 添加
Course[] arr = {new Course("3","離散數學"), new Course("4","設計模式")};
list.addAll(Arrays.asList(arr));
3. 刪
| 方法 | 說明 |
remove(Object o) | 按對象刪除(需正確 equals) |
remove(int index) | 按索引刪除(推薦) |
removeAll(Collection<?> c) | 批量刪除 |
4. 改
list.set(0, new Course("5","計算機網絡")); // 實質:新對象替換舊位置
5. 查與遍歷
// 1. 索引獲取
Course c = list.get(0);
// 2. 迭代器(通用,可刪除)
Iterator<Course> it = list.iterator();
while (it.hasNext()) {
Course cr = it.next();
// it.remove(); // 安全刪除
}
// 3. for-each(最常用,只讀)
for (Course cr : list) { ... }
// 4. 包含判斷(依賴 equals)
list.contains(obj);
list.containsAll(coll);
// 5. 索引查找
list.indexOf(obj); // 正序首次出現
list.lastIndexOf(obj); // 倒序首次出現
⚠️ 關鍵點:contains/remove 依賴 equals()
// 必須重寫 equals()(通常連帶 hashCode())
@Override
public boolean equals(Object obj) {
if (this == obj) return true;
if (!(obj instanceof Course)) return false;
Course other = (Course) obj;
return Objects.equals(this.name, other.name);
}
二、Set 接口詳解
實例化
Set<Course> set = new HashSet<>(); // 無序、不可重複
增刪改查與 List 類似,無索引相關方法。
HashSet 存儲依賴 hashCode() 與 equals(),自定義對象必須同時重寫兩者。
三、Map 接口詳解
實例化
Map<String, Student> map = new HashMap<>();
核心操作
| 操作 | 方法 |
| 增/改 | put(K key, V value)(Key 存在則覆蓋) |
| 刪 | remove(Object key) |
| 查-單值 | get(Object key) |
| 查-所有 Key | keySet() → 遍歷 Key 再 get() |
| 查-鍵值對 | entrySet() → 遍歷 Map.Entry<K,V>(推薦,性能最佳) |
| 查-所有 Value | values() |
| 存在性判斷 | containsKey(key) / containsValue(value) |
遍歷最佳實踐
// 方式 1:keySet(需兩次查找)
for (String key : map.keySet()) {
Student s = map.get(key);
}
// 方式 2:entrySet(推薦,一次查找)
for (Map.Entry<String, Student> entry : map.entrySet()) {
String key = entry.getKey();
Student val = entry.getValue();
}
// 方式 3:Java 8+ forEach
map.forEach((k, v) -> System.out.println(k + "=" + v));
四、Collections 工具類
1. 排序
// Integer/List 排序(自然順序)
List<Integer> nums = Arrays.asList(5, 2, 8, 1);
Collections.sort(nums); // [1, 2, 5, 8]
// String 排序(字典序:數字→大寫→小寫)
List<String> strs = Arrays.asList("microsoft", "google", "lenovo");
Collections.sort(strs); // [google, lenovo, microsoft]
// 自定義對象排序:實現 Comparable
class Student implements Comparable<Student> {
int age;
@Override public int compareTo(Student o) {
return Integer.compare(this.age, o.age); // 年齡升序
}
}
Collections.sort(studentList);
2. 二分查找(前提:已排序)
int index = Collections.binarySearch(sortedList, target);
3. 其他常用
reverse(list):反轉
shuffle(list):隨機打亂
frequency(coll, obj):統計出現次數
disjoint(coll1, coll2):判斷無交集
synchronizedList(list):返回線程安全視圖
五、比較器體系:Comparable vs Comparator
| 維度 | Comparable (內部比較器) | Comparator (外部比較器) |
| 位置 | 實體類實現 | 獨立類/匿名類/Lambda |
| 方法 | compareTo(T o) | compare(T o1, T o2) |
| 適用場景 | 自然順序(如數值、字典序) | 多種排序規則、無法修改實體類 |
| 使用 | Collections.sort(list) | Collections.sort(list, comparator) |
Comparator 靈活用法
// 多字段排序:先按年齡升序,年齡相同按姓名降序
Comparator<Student> cmp = Comparator
.comparing(Student::getAge)
.thenComparing(Student::getName, Comparator.reverseOrder());
Collections.sort(list, cmp);
// 或 Lambda 直接內聯
Collections.sort(list, (a, b) -> {
int ageCmp = Integer.compare(a.getAge(), b.getAge());
return ageCmp != 0 ? ageCmp : b.getName().compareTo(a.getName());
});
六、性能選型指南
| 場景 | 推薦實現 | 理由 |
| 頻繁隨機訪問、末尾增刪 | ArrayList | 底層數組,O(1) 訪問 |
| 頻繁頭部/中間增刪 | LinkedList | 雙向鏈表,O(1) 插入刪除 |
| 去重、集合運算 | HashSet | O(1) contains/add |
| 保持插入順序去重 | LinkedHashSet | 鏈表維護順序 |
| 有序集合、範圍查詢 | TreeSet | 紅黑樹,O(log n) |
| 鍵值映射、高頻查找 | HashMap | O(1) 平均 |
| 保持插入順序 Map | LinkedHashMap | LRU 緩存首選 |
| 有序 Map、範圍查詢 | TreeMap | 紅黑樹有序 |
總結
Java 集合框架設計精妙,核心在於:
- 接口與實現分離:面向接口編程,易於替換實現
- equals/hashCode 契約:Set/Map 正確性基石,自定義對象必重寫
- Comparable/Comparator 分離:自然順序 vs 定制順序
- 工具類 Collections:排序、查找、線程安全包裝一站式
實戰中根據「訪問模式、數據量、併發需求、順序要求」選型,事半功倍。