在 Java 集合框架中,TreeSet 需要元素實現 Comparable 介面以維持排序順序。本文透過一個學生類別 UpdateStu 的完整範例,詳細解析 compareTo 方法中巢狀三元運算子的邏輯,並展示如何利用 TreeSet 進行自然排序、頭部集合與子集合操作。
public class UpdateStu implements Comparable<UpdateStu> {
String name;
long id;
public UpdateStu(String name, long id) {
this.id = id;
this.name = name;
}
@Override
public int compareTo(UpdateStu o) {
UpdateStu upstu = o;
// 巢狀三元運算子:比較兩個 long 型別 ID
int result = id > upstu.id ? 1 : (id == upstu.id ? 0 : -1);
return result;
}
// getter / setter 省略...
}
id > upstu.id ? 1 : ...:若當前物件 ID 大於參數物件 ID,回傳 1,表示「大於」。id == upstu.id ? 0 : -1:若不大於,再判斷是否相等;相等回傳 0,否則回傳 -1(表示「小於」)。Long.compare(id, upstu.id),但手寫邏輯有助於理解比較器原理。public static void main(String[] args) {
UpdateStu stu1 = new UpdateStu("李同學", 01011);
UpdateStu stu2 = new UpdateStu("陳同學", 01021);
UpdateStu stu3 = new UpdateStu("王同學", 01051);
UpdateStu stu4 = new UpdateStu("馬同學", 01012);
TreeSet<UpdateStu> tree = new TreeSet<>();
tree.add(stu1); tree.add(stu2); tree.add(stu3); tree.add(stu4);
// 1. 自然排序輸出(依 ID 升冪)
System.out.println("Set集合中的所有元素:");
for (UpdateStu stu : tree) {
System.out.println(stu.getId() + " " + stu.getName());
}
// 2. headSet:嚴格小於 stu2 的元素
System.out.println("\n截取前面部分的集合:");
for (UpdateStu stu : tree.headSet(stu2)) {
System.out.println(stu.getId() + " " + stu.getName());
}
// 3. subSet:包含 stu2、不包含 stu3 的區間
System.out.println("\n截取中間部分的集合");
for (UpdateStu stu : tree.subSet(stu2, stu3)) {
System.out.println(stu.getId() + " " + stu.getName());
}
}
Set集合中的所有元素: 1011 李同學 1012 馬同學 1021 陳同學 1051 王同學 截取前面部分的集合: 1011 李同學 1012 馬同學 截取中間部分的集合 1021 陳同學
TreeSet、Collections.sort 等排序 API 使用。compareTo 判定),自動維持升冪順序,提供 headSet、tailSet、subSet 等篩選方法。01011 為八進位,實際值為 521(十進位),建議生產碼避免使用前導零以免誤解。compareTo 中直接相減 return (int)(id - upstu.id):長整數相減可能溢位導致符號錯誤。Long.compare(id, upstu.id)(Java 7+)或巢狀三元運算子,安全且可讀。Comparable<T> 泛型版本,避免非必要的型別轉換與 ClassCastException。