Eigene Ordnung in Tree-Collections
Übergeben Sie TreeMap bzw. TreeSet einen Comparator, um domänenspezifische Sortierreihenfolgen festzulegen.
Eigene Ordnung in Tree-Collections ist eine kostenlose Java Academy-Lektion auf CoddyKit. Dies ist Lektion 4 von 4. Du kannst die komplette Lektion unten kostenlos lesen – dann übst du sie direkt im Browser mit einem integrierten Code-Editor und einem KI-Tutor rund um die Uhr. Sie ist Teil des Java Academy-Lernpfads, und dein Fortschritt wird über Web und CoddyKit-App synchronisiert. Der Java Academy-Kurs umfasst insgesamt 4 Lektionen.
Warum eine benutzerdefinierte Ordnung?
Tree-Sammlungen (TreeMap, TreeSet) verwenden standardmäßig die natürliche Ordnung. Wenn Ihre Domänenobjekte keine natürliche Ordnung haben oder Sie eine andere Sortierung benötigen, übergeben Sie beim Erstellen einen Comparator.
Comparator beim Erstellen einer TreeMap
Übergeben Sie einen Comparator, um Schlüssel nach einer benutzerdefinierten Regel zu sortieren – zum Beispiel in umgekehrter alphabetischer Reihenfolge:
import java.util.*;
TreeMap<String, Integer> map = new TreeMap<>(Comparator.reverseOrder());
map.put("banana", 2);
map.put("apple", 1);
map.put("cherry", 3);
map.forEach((k,v) -> System.out.println(k)); // cherry, banana, appleComparator beim Erstellen eines TreeSet
Übergeben Sie TreeSet einen Comparator, um die Sortierreihenfolge unabhängig von der natürlichen Ordnung der Elemente festzulegen:
TreeSet<String> byLength = new TreeSet<>(
Comparator.comparingInt(String::length)
.thenComparing(Comparator.naturalOrder())
);
byLength.addAll(List.of("fig","apple","kiwi","date","banana"));
for (String s : byLength) System.out.print(s + " ");
// fig date kiwi apple bananaObjekte nach mehreren Feldern sortieren
Verketten Sie Comparators, um zunächst nach einem primären Feld und bei Gleichstand nach einem sekundären Feld zu sortieren:
record Employee(String name, String dept, int salary) {}
TreeSet<Employee> sorted = new TreeSet<>(
Comparator.comparing(Employee::dept)
.thenComparingInt(Employee::salary).reversed()
.thenComparing(Employee::name)
);
sorted.add(new Employee("Alice", "Eng", 90_000));
sorted.add(new Employee("Bob", "Eng", 85_000));
sorted.add(new Employee("Carol", "HR", 70_000));
for (Employee e : sorted) System.out.println(e.dept()+" "+e.name());Konsistenz mit equals
Wichtige Regel: Der von TreeSet/TreeMap verwendete Comparator definiert die Gleichheit für die Sammlung. Wenn comparator.compare(a, b) == 0, gelten a und b als derselbe Schlüssel – selbst wenn a.equals(b) false ist.
// Comparator ignoring case — "apple" and "APPLE" become the same key!
TreeSet<String> ci = new TreeSet<>(String.CASE_INSENSITIVE_ORDER);
ci.add("apple");
ci.add("APPLE"); // not added — same by comparator
System.out.println(ci.size()); // 1TreeMap ohne Beachtung der Groß-/Kleinschreibung
Ein häufiger praktischer Anwendungsfall: eine TreeMap, deren Schlüssel Zeichenfolgen sind, bei denen die Groß-/Kleinschreibung ignoriert wird (nützlich für HTTP-Header und Konfigurationsschlüssel):
TreeMap<String, String> headers = new TreeMap<>(String.CASE_INSENSITIVE_ORDER);
headers.put("Content-Type", "application/json");
headers.put("content-type", "text/html"); // overwrites!
System.out.println(headers.get("CONTENT-TYPE")); // text/html
System.out.println(headers.size()); // 1Null-sicherer Comparator
Tree-Sammlungen mit natürlicher Ordnung lösen bei Null-Schlüsseln eine NPE aus. Verwenden Sie einen null-sicheren Comparator, um null als kleinsten Schlüssel zuzulassen:
TreeMap<String, Integer> map = new TreeMap<>(
Comparator.nullsFirst(Comparator.naturalOrder())
);
map.put(null, 0);
map.put("b", 2);
map.put("a", 1);
map.forEach((k,v) -> System.out.println(k + "=" + v));
// null=0, a=1, b=2Beispiel für ein Domänenobjekt: Produkte nach Preis
Sortieren Sie Produkte in einem TreeSet nach dem Preis, mit dem Namen als Tie-Breaker, damit die Eindeutigkeit erhalten bleibt:
record Product(String name, double price) {}
TreeSet<Product> catalog = new TreeSet<>(
Comparator.comparingDouble(Product::price)
.thenComparing(Product::name)
);
catalog.add(new Product("Widget", 9.99));
catalog.add(new Product("Gadget", 24.99));
catalog.add(new Product("Donut", 9.99));
catalog.forEach(p -> System.out.println(p.name() + " $" + p.price()));
// Donut $9.99, Widget $9.99, Gadget $24.99Comparator abrufen
Rufen Sie comparator() für eine TreeMap oder ein TreeSet auf, um den benutzerdefinierten Comparator abzurufen. Bei Verwendung der natürlichen Ordnung wird null zurückgegeben.
TreeMap<String, Integer> map = new TreeMap<>(Comparator.reverseOrder());
System.out.println(map.comparator() != null); // true
TreeMap<String, Integer> natural = new TreeMap<>();
System.out.println(natural.comparator()); // nullZusammensetzen von Comparators
Javas Comparator bietet verkettbare Factory-Methoden für eine übersichtliche Zusammensetzung:
Comparator<String> comp =
Comparator.comparingInt(String::length) // by length
.thenComparing(Comparator.naturalOrder()); // then alphabetically
TreeSet<String> ts = new TreeSet<>(comp);
ts.addAll(List.of("go", "java", "c", "rust", "py"));
ts.forEach(s -> System.out.print(s + " "));
// c go py java rustWann Sie KEINEN benutzerdefinierten Comparator verwenden sollten
Vermeiden Sie bei TreeMap-Schlüsseln und TreeSet-Elementen einen Comparator, der nicht mit equals konsistent ist – dies führt zu verwirrenden „fehlenden“ Einträgen. Stellen Sie für ein korrektes Verhalten in allen Sammlungskontexten sicher, dass compare(a, b) == 0 genau dann gilt, wenn a.equals(b) true ergibt.
Kurzer Test
Ein TreeSet verwendet einen Comparator, der ausschließlich auf String::length basiert. Was passiert, wenn Sie sowohl "cat" als auch "dog" hinzufügen?
Rückblick: Benutzerdefinierte Sortierung
Die wichtigsten Punkte:
- Übergeben Sie dem Konstruktor von TreeMap/TreeSet einen Comparator, um eine benutzerdefinierte Sortierreihenfolge festzulegen
- Die vom Comparator definierte Gleichheit bestimmt die Eindeutigkeit in Baumkollektionen
- Stellen Sie sicher, dass der Comparator mit equals konsistent ist, um unerwartete Ergebnisse zu vermeiden
- Verwenden Sie Comparator.nullsFirst/nullsLast für eine null-sichere Sortierung
- Verketten Sie Vergleiche mit thenComparing, um nach mehreren Feldern zu sortieren
Häufig gestellte Fragen
Ist die Lektion „Eigene Ordnung in Tree-Collections“ kostenlos?
Ja — der vollständige Text von „Eigene Ordnung in Tree-Collections“ ist hier im Web kostenlos zu lesen. Um sie interaktiv zu üben (integrierter Code-Editor und 24/7 KI-Tutor) und den Rest des Java Academy-Kurses freizuschalten, upgrade auf CoddyKit PRO. Der Java Academy-Kurs umfasst insgesamt 4 Lektionen.
Was lerne ich in „Eigene Ordnung in Tree-Collections“?
Übergeben Sie TreeMap bzw. TreeSet einen Comparator, um domänenspezifische Sortierreihenfolgen festzulegen. Du übst Java Academy mit praktischem Code, den du direkt im Browser ausführst, und ein 24/7 KI-Tutor beantwortet deine Fragen während du die Lektion bearbeitest.
Brauche ich Erfahrung, um Java Academy zu starten?
Keine Vorkenntnisse erforderlich. Java Academy auf CoddyKit ist für Anfänger bis fortgeschrittene Lernende strukturiert, sodass du hier starten oder von Anfang an beginnen und in deinem eigenen Tempo voranschreiten kannst. Dies ist Lektion 4 von 4.
Wie lange dauert die Lektion „Eigene Ordnung in Tree-Collections“?
Die meisten CoddyKit-Lektionen dauern etwa 5–10 Minuten. Jede ist kompakt und interaktiv, sodass du stetig Fortschritte machst und genau dort weitermachst, wo du aufgehört hast – im Web und in der App.
Kann ich in dieser Java Academy-Lektion Code schreiben und ausführen?
Ja. Jede Java Academy-Lektion enthält einen integrierten Code-Editor, sodass du echten Code direkt in deinem Browser schreibst und ausführst und sofort KI-Feedback erhältst — ohne lokale Einrichtung erforderlich.
Alle Lektionen in diesem Kurs
- TreeMap: Sortierte Schlüssel-Wert-Paare
- Teil-Maps und Bereichsansichten
- TreeSet und NavigableSet
- Eigene Ordnung in Tree-Collections