{
"llm" : {
"feedback" : "# Exercise: address\n\n### Correctness\n- `getCity()` wirft eine `IllegalArgumentException`, wenn `city` leer ist; gefordert ist dieses Verhalten nur für Konstruktor und Setter, nicht für Getter.\n\n### Suggestion\n- Überlege, wo Invarianten geprüft werden müssen, damit ein Objekt nie in einen ungültigen Zustand kommt. Wenn du das im Konstruktor und in den Settern sicherstellst, sollte ein Getter normalerweise nur den aktuellen Wert zurückgeben, statt zu validieren/Exceptions zu werfen.\n\n### Code Style\n- Du wiederholst die gleichen Validierungschecks und Fehlermeldungen an mehreren Stellen (Konstruktor + Setter). Das lässt sich zentralisieren (z.B. über private Hilfsmethoden), damit du Logik nur einmal pflegen musst.\n- In den Fehlermeldungen beim `zipCode` steht „muss positiv sein“, obwohl du eigentlich „positiv und vierstellig“ prüfst; benenne die Messages konsistent zu der tatsächlichen Bedingung.\n\n\n# Exercise: timespan\n\n### Correctness\n- Im Konstruktor werden keine Preconditions für negative Eingaben durchgesetzt: `add(hours, minutes)` lässt z.B. `new TimeSpan(-1, 0)` zu, weil deine Negativprüfung in `add` nur den *aktuellen* Zustand (`totalMinutes()`) prüft, nicht die übergebenen Parameter.\n- In `add` wird die Precondition für „Zeitspannen können nur verlängert werden“ nicht korrekt geprüft: `if (totalMinutes() >= this.minutes)` vergleicht Minuten mit Gesamtminuten und hat nichts mit „neu ≥ alt“ zu tun.\n- Negative Werte in `add(hours, minutes)` werden nicht zuverlässig abgefangen; dadurch kann `totalMinutes` nach dem Addieren negativ werden, was laut Aufgabe nicht passieren darf.\n- Die Invariante `0 ≤ getMinutes ≤ 59` ist nicht garantiert: `checkMinutes()` korrigiert zwar bei `minutes >= 60`, aber bei negativen Minuten ist die Logik unvollständig und kann `minutes` weiterhin negativ lassen bzw. `hours` falsch anpassen.\n\n### Suggestion\n- Prüfe im Konstruktor (oder in `add`) die *Parameter* `hours` und `minutes` direkt auf negative Werte, bevor du sie übernimmst.\n- Für „nur verlängern“ brauchst du einen Vergleich zwischen „alter totalMinutes“ und „neuer totalMinutes nach dem Add“: Überlege dir, wie du den alten Wert zwischenspeicherst und den neuen Wert berechnest, bevor du die Felder veränderst.\n- Achte darauf, dass du die Exception wirfst, **bevor** du den internen Zustand änderst, wenn die Precondition verletzt wird.\n- Für die Minuten-Normalisierung: Überlege dir eine robuste Umrechnung, die nach jedem Add sicherstellt, dass `minutes` am Ende im Bereich 0..59 liegt (und dabei die Stunden entsprechend angepasst werden) – insbesondere auch dann, wenn Minuten negativ werden könnten.\n\n### Code Style\n- `this.totalMinutes();` in `add` macht nichts (Rückgabewert wird ignoriert) und kann entfernt werden.\n- Fehlermeldung `\"negativ\"` ist wenig aussagekräftig; eine klarere Message hilft beim Debuggen (z.B. welche Werte waren ungültig).\n- `checkMinutes()` mischt Korrektur für `>=60` und `<0`, aber die `<0`-Variante ist schwer nachvollziehbar (und derzeit nicht symmetrisch zur `>=60`-Korrektur); wenn du Negatives sowieso verbietest, könntest du die Methode vereinfachen.\n- Ein konsistenter Klammer-/Whitespace-Stil (z.B. Leerzeichen nach `if (`) verbessert die Lesbarkeit.\n\n\n# Exercise: asteroids\n\nLlm Evaluation ist für diese Aufgabe deaktiviert. Entferne die .llmignore Datei vom Package der Aufgabe.\n\n\n# Exercise: bosses\n\n### Correctness\n- In `findCommonSuperiorWith(other)` ist der erste `while`-Loop so gebaut, dass du sofort mit `commonSuperior` (also `this`) gegen `superior` (startet bei `other`) vergleichst und dann **`commonSuperior` zurückgibst**, sobald beide gleich sind. Damit würdest du in Fällen, wo `this` irgendwo in der Boss-Kette von `other` vorkommt, immer `this` zurückgeben – das ist zwar manchmal richtig, aber diese Prüfung ist an der Stelle redundant und kann bei einer falschen späteren Anpassung leicht zu Logikfehlern führen; der “erste gemeinsame Vorgesetzte” sollte systematisch über die beiden Ketten bestimmt werden.\n- In `findCommonSuperiorWith(other)` verwendest du einmal `commonSuperior.equals(superior)` statt Identitätsvergleich (`==`). Da `Employee` `equals` nicht überschreibt, ist das aktuell zufällig identisch zu `==`, aber die Aufgabe bezieht sich auf die konkrete Person/Instanz in der Hierarchie; ein gemischter Vergleich kann zu falschem Verhalten führen, sobald `equals` irgendwann doch implementiert würde (z.B. nur nach `name`).\n\n### Suggestion\n- Überlege bei `findCommonSuperiorWith`: Bau zuerst **eine** vollständige Menge/Liste der Vorgesetzten (inkl. der Person selbst) von *einer* Seite auf, und suche dann beim Hochlaufen der *anderen* Seite den ersten Treffer. Dann brauchst du keinen speziellen “Sofortvergleich” am Anfang und vermeidest, dass du “aus Versehen” immer `this` bevorzugst.\n- Entscheide dich konsequent für **Identität vs. Gleichheit**: Wenn “dieselbe Person” im Sinne “dasselbe Objekt in der Kette” gemeint ist, bleib überall bei `==` (und entsprechend auch bei Membership-Checks in Collections darauf achten, was verglichen wird).\n\n### Code Style\n- `import java.util.ArrayList;` ist nur für `findCommonSuperiorWith` nötig; falls du später umstellst (z.B. auf `Set`), Import entsprechend anpassen/aufräumen.\n- Benennung: `commonSuperior` wird erst als `this` benutzt und dann als Laufvariable die Boss-Kette hochgeschoben – das macht den Code schwerer zu lesen. Zwei Variablen (eine für Startpunkt, eine als Cursor) wären klarer.\n- `ArrayList<Employee> bosses = new ArrayList<Employee>();` kann in modernem Java mit Diamond-Operator geschrieben werden (`new ArrayList<>()`).\n- `bosses.contains(...)` auf einer `ArrayList` ist linear; für größere Hierarchien wäre eine `Set`-Struktur passender (Lesbarkeit/Intention: “Mitgliedschaftstest”).\n\n\n# Exercise: smarthome\n\n### Correctness\n- In `turnNextRoomBright` schaltest du nur die Lampen ein/auf 1.0, bis du zum ersten „nicht hellen“ Exemplar kommst; danach bleiben die übrigen Lampen im selben Raum ggf. unverändert, obwohl laut Aufgabe *alle* Lampen in diesem Raum eingeschaltet und auf 1.0 gesetzt werden sollen.\n- In `nightMode` schaltest du in den Bedrooms nicht „je eine Lampe pro Bedroom“ ein, sondern (wegen `isOnB`) nur im ersten gefundenen Bedroom-Lampenblock; die restlichen Bedrooms bleiben dunkel.\n- In `nightMode` rufst du `findHallway()` und `findBedrooms()` innerhalb der innersten Lampen-Schleife auf und führst die „Nachtmodus“-Logik mehrfach aus; dadurch ist das Verhalten unnötig oft wiederholt und kann (je nach Zustand/Timing) auch zu unerwarteten Zustandsänderungen führen, statt die Operation einmal sauber fürs ganze Haus anzuwenden.\n- In `nightMode` ist nicht garantiert, dass nach dem Ausschalten „aller anderen Lampen“ am Ende wirklich genau die gewünschten Lampen an sind, weil du während des Ausschaltens bereits wieder Lampen einschaltest (verschachtelte Schleifen), wodurch spätere Iterationen wieder Lampen ausschalten können, die du zuvor für den Nachtmodus eingeschaltet hast (besonders wenn Hallway/Bedroom-Lampen im äußeren Durchlauf erneut erreicht werden).\n\n### Suggestion\n- Für `turnNextRoomBright`: Überlege dir eine Logik in zwei Phasen: (1) Finde den ersten Raum, der nicht komplett „on & brightness==1.0“ ist. (2) Wenn du ihn gefunden hast, iteriere **nochmals** über alle Lampen dieses Raums und setze sie alle auf an + 1.0.\n- Für `nightMode`: Trenne klar die Schritte „alles ausschalten“ und „gewünschte Lampen einschalten“. Wenn du zuerst wirklich alle Lampen im ganzen Haus ausschaltest und **danach** Hallway + Bedrooms behandelst, verhinderst du, dass spätere Schleifen deine Nachtmodus-Lampen wieder ausschalten.\n- Für `nightMode` (Bedrooms): Du brauchst pro Bedroom eine eigene Auswahl „erste/beliebige Lampe“—also ein Flag/Mechanismus pro Raum (oder eine Schleife, die beim ersten Lampenfund in diesem Raum stoppt), nicht ein einziges `isOnB` für alle Bedrooms zusammen.\n- Für `nightMode`: Rufe `findHallway()` und `findBedrooms()` einmalig auf (z.B. am Anfang der Methode) und arbeite dann mit den Ergebnissen weiter, statt sie in einer tiefen Schleife immer wieder neu zu berechnen.\n\n### Code Style\n- Unnötige Imports: `Objects` wird nur für String-Vergleich genutzt (kann man machen, aber nicht nötig), und `Random` wird mehrfach neu erzeugt; `Objects` ist ok, aber `Random r = new Random()` innerhalb der Lampen-Schleife ist unnötig.\n- In `randomize` erzeugst du zwei `Random`-Objekte (`generator` und `r`), wobei eins davon in der inneren Schleife neu erstellt wird; besser ist, ein einziges Random-Objekt zu verwenden.\n- `nightMode` ist sehr stark verschachtelt (Room→Lamp→(findHallway/findBedrooms)→…); das erschwert das Verständnis. Eine flachere Blockstruktur mit klaren Teilaufgaben (z.B. erst alles off, dann Hallway, dann Bedrooms) wäre deutlich lesbarer.\n- Kleinigkeit: In mehreren Methoden prüfst du `if(room.getLamps() != null)`. Laut Vorlage wirkt es so, als ob `lamps` immer gesetzt wird; falls das wirklich garantiert ist, sind diese Checks eher Rauschen.\n",
"status" : "SUCCESS"
}
}