MINT lernen

Übungen: Eine Klasse implementieren

Aus drei Feldern einer Klassenkarte wird echter Java-Code — und ein vergessenes this kann ein ganzes Regal leer lassen.

Dein Fortschritt:
0 / 0 Aufgaben
1

Übungsaufgaben

Zehn Übungen zum Klicken, Ziehen und Knobeln — von AFB I bis AFB III. Jede Übung gibt dir sofort Rückmeldung; wenn du hängst, helfen dir die gestuften Tipps.

A1
Eine Klasse lesen: Parkticket
AFB I

So ist das Ticket eines Parkhauses implementiert. Welche Aussagen stimmen?

public class Parkticket {
    private int einfahrtMinute;
    private boolean bezahlt;

    public Parkticket(int einfahrtMinute) {
        this.einfahrtMinute = einfahrtMinute;
        bezahlt = false;
    }

    public int dauer(int jetzt) {
        return jetzt - einfahrtMinute;
    }

    public void bezahlen() {
        bezahlt = true;
    }
}
Mehrere Antworten sind richtig. Markiere alle zutreffenden und klicke dann auf „Prüfen“.
Eine void-Methode darf keinen Wert zurückgeben — return true; wäre sogar ein Übersetzungsfehler. this ist nur nötig, wenn ein Parameter genauso heißt wie das Attribut; bei bezahlt = false; gibt es keinen gleichnamigen Parameter, also ist das Attribut gemeint. Und die Attribute gehören zum Objekt, sobald es mit new erzeugt wird.
Ansatz: Gehe die Klasse von oben nach unten durch: Attribute, Konstruktor, Methoden. Was unterscheidet den Konstruktorkopf von einem Methodenkopf?
Weiter: this braucht man nur, wenn Parameter und Attribut gleich heißen. void heißt: kein return mit Wert.
A2
Bausteine einer Java-Klasse
AFB I

Zeilen aus der Klasse Song einer Musik-App. Sortiere sie nach ihrer Rolle.

Ziehe jede Karte in den passenden Korb — oder wähle sie mit Enter aus und drücke dann die Ziffer des Korbs (0 legt sie zurück).
1Attribut
2Konstruktor
3Methode mit Rückgabe
4Methode ohne Rückgabe
Der Konstruktor ist die einzige Zeile ohne Rückgabetyp, die genauso heißt wie die Klasse. Attribute enden mit Semikolon und haben keine Klammern. Typischer Fehler: istLang() zu den Methoden ohne Rückgabe legen, weil sie nichts „holt“ — sie liefert aber einen boolean. Nur void bedeutet: keine Rückgabe.
Ansatz: Achte auf das Wort direkt vor dem Namen: ein Datentyp, void oder gar nichts?
Weiter: Kein Rückgabetyp und Name wie die Klasse → Konstruktor. Semikolon ohne Klammern → Attribut.
A3
Vom Diagramm zum Quelltext
AFB I

Ein Sportverein hat die Klasse Mitglied entworfen. Setze die Java-Schlüsselwörter ein — eines bleibt übrig.

Mitglied
  • - name: Zeichenkette
  • - aktiv: Wahrheitswert
  • - beitrag: Ganzzahl
  • c Mitglied(name: Zeichenkette)
  • + beitragZahlen(betrag: Ganzzahl)
  • + getBeitrag(): Ganzzahl
Wort anklicken, dann Lücke anklicken (oder umgekehrt) — mit Tab und Enter geht es genauso. Ein Klick auf eine gefüllte Lücke legt das Wort zurück.

Aus „- name: Zeichenkette“ wird private name; und aus „- aktiv: Wahrheitswert“ wird private aktiv;. Im Konstruktor steht .name = name;. Die Methode beitragZahlen bekommt den Rückgabetyp . In getBeitrag muss eine -Anweisung stehen.

new bleibt übrig: Es gehört nicht in die Klasse, sondern dorthin, wo ein Objekt erzeugt wird, z. B. new Mitglied("Lea"). Häufig verwechselt: Wahrheitswert wird zu boolean, nicht zu bool oder Boolean.
Ansatz: Übersetze die Datentypen: Zeichenkette → ?, Wahrheitswert → ?
Weiter: Ohne Rückgabetyp im Diagramm schreibt man in Java void. Ein Getter liefert seinen Wert mit return. this unterscheidet Attribut und gleichnamigen Parameter.
A4
Stimmt's? — Pizzen erzeugen
AFB II

Die Klasse Pizza ist fertig implementiert. In einer anderen Klasse stehen diese drei Zeilen:

Pizza
  • - sorte: Zeichenkette
  • - preis: Ganzzahl
  • - belag: Zeichenkette
  • c Pizza(sorte: Zeichenkette, preis: Ganzzahl)
  • + belegen(zutat: Zeichenkette)
  • + getPreis(): Ganzzahl
Pizza p = new Pizza("Funghi", 8);
Pizza q = new Pizza("Funghi", 8);
p.belegen("Oliven");
Fünf Aussagen nacheinander. Eine falsche Einschätzung reicht — dann startest du die Serie mit „Neue Runde“ neu.
Aussage 1 von 5

Merksatz: new + Konstruktor erzeugt ein Objekt; Methoden ruft man mit Punktnotation an einem bestimmten Objekt auf — nie an der Klasse.
Ansatz: Zähle die new — so viele Objekte gibt es.
Weiter: Vor dem Punkt steht immer das Objekt, auf das die Methode wirkt.
A5
Diagrammzeile trifft Java-Zeile
AFB II

Die Verkehrsbetriebe übersetzen ihre Klasse Haltestelle nach Java. Verbinde jede Zeile der Klassenkarte mit der passenden Java-Zeile.

Haltestelle
  • - name: Zeichenkette
  • - barrierefrei: Wahrheitswert
  • - wartezeit: Fließkommazahl
  • c Haltestelle(name: Zeichenkette)
  • + getWartezeit(): Fließkommazahl
  • + istBarrierefrei(): Wahrheitswert
  • + verspaetung(minuten: Ganzzahl)
Ansatz: Ordne zuerst die drei Attribute zu: Welche Java-Zeilen enden mit Semikolon und haben keine Klammern?
Weiter: Bei den Methoden: Welcher Typ steht vorn? Fließkommazahl → double, Wahrheitswert → boolean, keiner → void.
A6
Wie viel hat es geregnet?
AFB IIMix

An der Wetterstation der Schule misst ein Regenmesser die Niederschlagsmenge in mm. Fehlerhafte Messungen (negative Werte) sollen ignoriert werden.

public class Regenmesser {
    private int summe;
    private int messungen;

    public Regenmesser() {
        summe = 0;
        messungen = 0;
    }

    public void messen(int mm) {
        if (mm >= 0) {
            summe = summe + mm;
            messungen = messungen + 1;
        }
    }

    public int durchschnitt() {
        return summe / messungen;
    }
}
Regenmesser r = new Regenmesser();
r.messen(4);
r.messen(-2);
r.messen(7);
r.messen(0);
r.messen(6);

Welchen Wert liefert r.durchschnitt()?

Rechne selbst und trage das Ergebnis ein — Enter prüft direkt.
Die Messung −2 wird durch die Verzweigung übersprungen; 0 ist aber gültig und zählt mit. Also summe = 4 + 7 + 0 + 6 = 17 und messungen = 4. 17 / 4 ist in Java bei zwei int-Werten eine Ganzzahldivision (Kapitel 1): Ergebnis 4, nicht 4,25. Häufige Fehler: 4,25 (Kommadivision), 3 (die −2 doch mitgezählt: 15 / 5) oder 5 (die 0 übersprungen: 17 / 3).
Ansatz: Verfolge summe und messungen nach jedem Aufruf. Welche Aufrufe erfüllen die Bedingung mm >= 0?
Weiter: Achtung: 0 >= 0 ist wahr. Und int / int schneidet in Java die Nachkommastellen ab.
A7
Rückgabewerte im Aquarium ordnen
AFB II

Eine Zoohandlung verwaltet ihre Becken mit dieser Klasse:

public class Aquarium {
    private int liter;
    private int fische;
    private int temperatur;

    public Aquarium(int liter) {
        this.liter = liter;
        fische = 0;
        temperatur = 20;
    }

    public void einsetzen(int anzahl) {
        fische = fische + anzahl;
    }

    public void heizen(int grad) {
        temperatur = temperatur + grad;
    }

    public int getTemperatur() {
        return temperatur;
    }

    public int literProFisch() {
        return liter / fische;
    }

    public int platzFuerWeitere() {
        return liter / 10 - fische;
    }
}
Aquarium a = new Aquarium(120);
a.einsetzen(4);
a.heizen(5);
a.einsetzen(2);
Aquarium b = new Aquarium(40);
b.einsetzen(1);

Sortiere die Aufrufe nach ihrem Rückgabewert — der kleinste zuerst.

Ziehe die Karten in die richtige Reihenfolge — mit der Tastatur: ↑/↓ verschiebt, Shift+↑/↓ wechselt nur den Fokus.
1b.platzFuerWeitere()
2a.platzFuerWeitere()
3a.literProFisch()
4a.getTemperatur()
5b.literProFisch()
Werte: b.platzFuerWeitere() = 40 / 10 − 1 = 3, a.platzFuerWeitere() = 120 / 10 − 6 = 6, a.literProFisch() = 120 / 6 = 20, a.getTemperatur() = 20 + 5 = 25, b.literProFisch() = 40 / 1 = 40. Oft verrutscht a.platzFuerWeitere(), wenn man den zweiten Aufruf a.einsetzen(2) übersieht — a hat 6 Fische, nicht 4. Und: a und b sind zwei Objekte mit getrennten Attributen.
Ansatz: Lege für a und b je eine kleine Objektkarte an (liter, fische, temperatur).
Weiter: a hat am Ende 6 Fische und 25 Grad, b hat 1 Fisch und 20 Grad. Rechne dann jede Methode aus.
A8
Die Kopierkarte der Schule
AFB III

Im Schulkopierer wird mit einer Karte bezahlt (Guthaben in Cent). Eine Schwarz-Weiß-Seite kostet 5 Cent, eine Farbseite 20 Cent.

public class Kopierkarte {
    private int guthaben;
    private int kopien;

    public Kopierkarte(int guthaben) {
        this.guthaben = guthaben;
        kopien = 0;
    }

    public void aufladen(int cent) {
        if (cent > 0) {
            guthaben = guthaben + cent;
        }
    }

    public boolean kopieren(int seiten, boolean farbig) {
        int preis = seiten * 5;
        if (farbig) {
            preis = seiten * 20;
        }
        if (preis <= guthaben) {
            guthaben = guthaben - preis;
            kopien = kopien + seiten;
            return true;
        }
        return false;
    }

    public int getGuthaben() {
        return guthaben;
    }

    public int getKopien() {
        return kopien;
    }
}
Kopierkarte karte = new Kopierkarte(200);
karte.kopieren(12, false);
karte.kopieren(8, true);
karte.aufladen(-50);
karte.kopieren(6, true);
karte.aufladen(100);
karte.kopieren(30, false);
Rechne die Kette Schritt für Schritt: Erst wenn ein Schritt stimmt, wird der nächste freigeschaltet. Enter prüft.
  1. Guthaben direkt nach dem ersten kopieren-Aufruf Cent
  2. Wie viele der vier kopieren-Aufrufe liefern true? Aufrufe
  3. Rückgabewert von karte.getKopien() am Ende Seiten
  4. Transfer: Wie viele Schwarz-Weiß-Seiten könnte man mit dem Endguthaben noch höchstens kopieren? Seiten
Verlauf: 200 → 140 (12 Seiten s/w); 8 Farbseiten = 160 Cent > 140 → abgelehnt; aufladen(−50) wird durch die Prüfung ignoriert; 6 Farbseiten = 120 → 20; aufladen(100) → 120; 30 s/w-Seiten = 150 > 120 → abgelehnt. Also 2 erfolgreiche Aufrufe, 12 + 6 = 18 Seiten und 120 / 5 = 24 Seiten. Typische Fehler: die abgelehnten Aufrufe trotzdem abbuchen oder das negative Aufladen abziehen.
Ansatz: Führe eine Tabelle mit guthaben und kopien und prüfe bei jedem Aufruf zuerst die Bedingung.
Weiter: Bei kopieren wird nur gebucht, wenn preis <= guthaben. Bei aufladen wird nur gebucht, wenn cent > 0.
A9
Fehlersuche: Konzertticket
AFB III

Die Klasse soll ein Konzertticket mit Platz und Preis beschreiben und sich mit new Ticket("A12", 49) erzeugen lassen. Drei Zeilen enthalten Fehler — zwei führen zu Übersetzungsfehlern, einer zu falschem Verhalten.

In diesem Text stecken Fehler. Klicke genau die falschen Zeilen an — die richtigen musst du stehen lassen.
Alle drei Fehler stehen ganz oben in der Liste typischer Klausurfehler: Konstruktor mit void, fehlendes this bei gleichnamigem Parameter und ein Getter ohne return. Tückisch ist der mittlere, denn er kompiliert — das Programm läuft, aber jedes Ticket kostet 0 Euro.
Ansatz: Prüfe drei Stellen besonders: den Konstruktorkopf, die Zuweisungen im Konstruktor und den Rumpf des Getters.
Weiter: Wenn Parameter und Attribut gleich heißen, meint der Name allein immer den Parameter. Ausgeben und Zurückgeben sind zwei verschiedene Dinge.
A10
Trickaufgabe: Ein Regal mit vier Fächern?
AFB IIITrick

Ein Lager nutzt diese Klasse. Jede Zeile unten startet mit einem neuen Regal: Regal r = new Regal(4); Welchen Wert liefert der letzte Aufruf der Zeile? Lies den Quelltext genau.

public class Regal {
    private int faecher;
    private int belegt;

    public Regal(int faecher) {
        faecher = faecher;
        belegt = 0;
    }

    public void einraeumen(int kisten) {
        if (belegt + kisten <= faecher) {
            belegt = belegt + kisten;
        }
    }

    public int getBelegt() {
        return belegt;
    }

    public int getFrei() {
        return faecher - belegt;
    }
}
Wähle für jede Zeile eine Stufe: 0 = Rückgabewert 0, 1 = Rückgabewert 1, 2 = Rückgabewert 2, 3 = Rückgabewert 3, 4 = Rückgabewert 4. Mit der Tastatur: Tab zur Zeile, ←/→ zwischen den Stufen, Enter setzt.
0 = Rückgabewert 04 = Rückgabewert 4
r.getFrei()
r.einraeumen(2); r.getBelegt()
r.einraeumen(-3); r.getFrei()
r.einraeumen(-2); r.einraeumen(1); r.getFrei()
r.einraeumen(-4); r.einraeumen(2); r.getFrei()
Der Trick steckt im Konstruktor: faecher = faecher; weist den Parameter sich selbst zu — das Attribut faecher bleibt 0. Deshalb ist nie Platz für positive Kistenzahlen (2 <= 0 ist falsch), während negative Werte durchrutschen: nach einraeumen(−3) ist belegt = −3 und getFrei() = 0 − (−3) = 3. Wer 4 und 2 erwartet hat, hat den Konstruktor so gelesen, wie er gemeint war — nicht, wie er programmiert ist. Korrektur: this.faecher = faecher;, und einraeumen sollte negative Werte ablehnen.
Ansatz: Welchen Wert hat das Attribut faecher nach dem Konstruktor wirklich?
Weiter: Ohne this meint faecher im Konstruktor den Parameter. Das Attribut bleibt beim Startwert 0 — rechne damit jede Zeile durch.