Generische Klassen
Teil des Abschnitts Objektorientierte Programmierung der Java-Journey von Coddy — Lektion 54 von 87.
Nachdem Sie nun verstehen, warum Generics nützlich sind, lassen Sie uns Ihre eigene generische Klasse erstellen. Eine generische Klasse deklariert einen oder mehrere Typparameter in spitzen Klammern nach dem Klassennamen, die dann in der gesamten Klasse verwendet werden können.
class Box<T> {
private T content;
public void set(T content) {
this.content = content;
}
public T get() {
return content;
}
}Das T ist ein Typparameter – ein Platzhalter, der durch einen tatsächlichen Typ ersetzt wird, wenn Sie eine Instanz erstellen. Sie können jeden beliebigen Namen verwenden, aber einzelne Großbuchstaben sind konventionell: T für Typ, E für Element, K für Key, V für Value.
Beim Instanziieren einer generischen Klasse geben Sie den tatsächlichen Typ in spitzen Klammern an:
Box<String> stringBox = new Box<>();
stringBox.set("Hello");
String value = stringBox.get(); // Kein Casting erforderlich
Box<Integer> intBox = new Box<>();
intBox.set(42);
Integer num = intBox.get();Beachten Sie den <> (Diamond-Operator) auf der rechten Seite — Java leitet den Typ aus der Deklaration ab. Sie können auch mehrere Typparameter für Klassen verwenden, die mit mehr als einem Typ arbeiten müssen:
class Pair<K, V> {
private K key;
private V value;
public Pair(K key, V value) {
this.key = key;
this.value = value;
}
public K getKey() { return key; }
public V getValue() { return value; }
}
Pair<String, Integer> pair = new Pair<>("age", 25);Aufgabe
EinfachLassen Sie uns ein Geschenkregistrierungssystem erstellen, das die Leistungsfähigkeit generischer Klassen demonstriert. Sie werden ein flexibles Aufbewahrungssystem erstellen, das jede Art von Geschenkartikel aufnehmen kann, sowie ein Register, das Empfängernamen mit ihren Geschenken unter Verwendung mehrerer Typparameter verknüpft.
Sie werden Ihren Code über drei Dateien organisieren:
GiftBox.java: Erstellen Sie eine generische Klasse, die jede Art von Geschenk verpacken kann. Ihre KlasseGiftBox<T>sollte ein privates Felditemvom TypTund ein privates Feldwrapped(boolean) haben, das mitfalsebeginnt. Fügen Sie einen Konstruktor hinzu, der das Element akzeptiert, eine MethodegetItem(), die das Element zurückgibt, eine Methodewrap(), die wrapped auf true setzt, und eine MethodeisWrapped(), die den Verpackungsstatus zurückgibt. Fügen Sie eine MethodegetStatus()hinzu, die entweder[item] (wrapped)oder[item] (unwrapped)zurückgibt, abhängig vom Verpackungszustand.Registry.java: Erstellen Sie eine generische Klasse mit zwei Typparametern, die einen Empfänger mit seinem Geschenk verknüpft. Ihre KlasseRegistry<K, V>sollte private Felderrecipientvom TypKundgiftvom TypVhaben. Fügen Sie einen Konstruktor hinzu, der beide Werte akzeptiert, Getter-MethodengetRecipient()undgetGift()sowie eine MethodegetEntry(), die Folgendes zurückgibt:[recipient] -> [gift]Main.java: Erwecken Sie Ihr Geschenkregister zum Leben! Sie erhalten drei Eingaben: einen Empfängernamen (String), eine Geschenkbehandlung (String) und einen Geschenkwert (Ganzzahl, die Dollar darstellt).Erstellen Sie zuerst eine
GiftBox<String>, die die Geschenkbehandlung enthält. Verpacken Sie diese mit der Methodewrap()und geben Sie dann ihren Status aus.Erstellen Sie als Nächstes eine
GiftBox<Integer>, die den Geschenkwert enthält (der einen Geschenkkartenbetrag darstellt). Verpacken Sie diese nicht – geben Sie ihren Status aus, um zu zeigen, dass sie unverpackt ist.Erstellen Sie schließlich eine
Registry<String, String>, die den Empfängernamen mit der Geschenkbehandlung verknüpft, und geben Sie den Registereintrag aus.
Sie erhalten drei Eingaben in der folgenden Reihenfolge: Empfängername, Geschenkbehandlung und Geschenkwert (als Ganzzahl).
Beachten Sie, wie dieselbe GiftBox-Klasse nahtlos mit den Typen String und Integer funktioniert – das ist die Schönheit von Generics! Und die Klasse Registry zeigt, wie mehrere Typparameter es Ihnen ermöglichen, flexible Paarungen zwischen zwei beliebigen Typen zu erstellen.
Probier es selbst
import java.util.Scanner;
class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
// Eingaben lesen
String recipientName = scanner.nextLine();
String giftDescription = scanner.nextLine();
int giftValue = scanner.nextInt();
// TODO: Erstelle eine GiftBox<String>, die die Geschenkbeschreibung enthält
// TODO: Verpacke sie mit der wrap()-Methode
// TODO: Gib ihren Status mit getStatus() aus
// TODO: Erstelle eine GiftBox<Integer>, die den Geschenkwert enthält
// TODO: Diese nicht verpacken - gib ihren Status aus (sollte als unverpackt angezeigt werden)
// TODO: Erstelle ein Registry<String, String>, das den Empfänger mit der Geschenkbeschreibung verknüpft
// TODO: Gib den Registereintrag mit getEntry() aus
}
}
Diese Lektion enthält ein kurzes Quiz. Starte die Lektion, um es zu beantworten und deinen Fortschritt zu speichern.
Alle Lektionen in Objektorientierte Programmierung
1Grundlagen der OOP
Externe DateienEinführung in die OOPKlassen vs. ObjekteDas this-SchlüsselwortMethodenFelder (Attribute)Konstruktor-MethodeKonstruktor-ÜberladungRückblick – Einfacher Taschenrechner4Vererbung
Grundlagen der Vererbung (extends)Das super-SchlüsselwortMethoden überschreiben (@Override)Konstruktor-VerkettungDie Object-KlasseEinfache & mehrstufige VererbungWarum keine Mehrfachvererbung von KlassenZusammenfassung - Mitarbeiter-Hierarchie7Spezielle Methoden & Object-Klasse
toString()-Methodeequals() und hashCode()clone()-MethodecompareTo() und ComparableComparator-InterfaceZusammenfassung – Benutzerdefiniertes Sortieren2Zugriffsmodifikatoren & Kapselung
Überblick über ZugriffsebenenGetter- und Setter-MethodenInformation HidingDas final-SchlüsselwortRückblick – Bankkonto-Manager5Polymorphismus
Grundlagen der MethodenüberladungMethodenüberschreibung (Laufzeit)Upcasting und DowncastingDer instanceof-OperatorAbstrakte Klassen und MethodenZusammenfassung – Formenrechner8Fortgeschrittene OOP-Konzepte
Komposition vs. VererbungAggregation vs. KompositionInnere, geschachtelte & anonyme KlassenEnums und Enum-MethodenRecords (Java 16+)Sealed Classes (Java 17+)11Design Patterns Teil 1
Einführung in Design PatternsSingleton-PatternFactory-PatternBuilder-PatternObserver-PatternStrategy-Pattern14Abschlussherausforderungen
E-Learning-PlattformBanksystemSpielcharakter-EntwicklungFahrzeugvermietung3Klasseneigenschaften & Statische Member
Instanz- vs. statische VariablenStatische MethodenStatische BlöckeKonstanten (static final)Zusammenfassung – Zähler & Utility6Interfaces & Abstrakte Klassen
Einführung in InterfacesInterfaces implementierenImplementierung mehrerer InterfacesDefault- & statische Methoden in InterfacesAbstrakte Klassen vs. InterfacesFunktionale InterfacesZusammenfassung - Zahlungssystem