{
"llm" : {
"feedback" : "# Exercise: fractal\n\n### Correctness\n- In `Boxes.drawRec` wird bei jedem Rekursionsschritt sofort ein Rechteck gezeichnet; dadurch werden auch bei `n > 0` grosse „Eltern“-Rechtecke gezeichnet, statt erst im Basisfall die kleinsten Kästchen zu zeichnen.\n- In `Boxes.drawRec` zeichnest du nur 3 der 4 Teil-Rechtecke (unten links fehlt), dadurch entsteht nicht das geforderte Box-Fraktal-Muster.\n- In `Triangles.drawRec` zeichnest du das Dreieck in jedem Rekursionsschritt, nicht nur im Basisfall; damit bekommst du nicht die erwartete rekursive Dreiecksstruktur, sondern überlagerte Linien aller Ebenen.\n- In `Triangles.drawRec` ist der Abbruchfall an `n < 0` gebunden; bei `n == 0` wird dennoch weiter rekursiv aufgerufen (mit `n-1`), was zusätzliche, nicht gewünschte Rekursionsstufen erzeugt.\n\n### Suggestion\n- Überlege dir für beide Formen einen klaren Basisfall (z.B. „wenn `n == 0`“) und zeichne die primitive Form (Rechteck/Dreieck) nur dort; in allen anderen Fällen solltest du nur die rekursiven Unteraufrufe machen.\n- Prüfe beim Box-Fraktal, welche vier Quadranten bei jeder Stufe entstehen und welche davon rekursiv weiter unterteilt bzw. direkt gezeichnet werden sollen; vergleiche das mit deinen aktuell 3 Aufrufen.\n- Bei den Dreiecken: Berechne die Mittelpunkte der drei Seiten und rufe dann die Rekursion nur für die drei „äusseren“ Dreiecke auf; achte darauf, dass bei `n == 0` keine weiteren Aufrufe mehr passieren.\n\n### Code Style\n- Entferne die auskommentierte alte `drawRec(...)`-Zeile in `Triangles`, damit der Code übersichtlich bleibt.\n- Vermeide es, Parameter wie `s` in `Boxes` wiederzuverwenden/zu überschreiben (`s = s/2`); ein neuer Variablenname (z.B. für die halbe Seitenlänge) macht die Rekursion leichter nachvollziehbar.\n\n\n# Exercise: knapsack\n\n### Correctness\n- Du berücksichtigst `maxN` nicht: In `pack` wird ein Item höchstens einmal geladen, obwohl laut Aufgabe jedes Item bis zu `n`-mal mitgenommen werden darf.\n- Das Zurücksetzen nach dem “Mehrfach-Laden” ist nicht korrekt umgesetzt, weil `unloadItem(i)` nur einmal entfernt; für die n-fach-Variante muss der Zustand nach dem Ausprobieren aller Varianten (0..n) wieder auf den Stand vor dem Item zurück.\n\n### Suggestion\n- Überlege dir für jedes Item `i`, wie viele Stück du davon einpacken willst (0, 1, 2, …, `maxN`) und wie du diese Möglichkeiten in der Rekursion systematisch durchprobieren kannst.\n- Achte darauf, dass du nach dem Durchspielen aller Stückzahlen für ein Item den Rucksackzustand (Gewicht/Wert) wieder exakt auf den Zustand vor diesem Item zurückbringst, bevor du zum vorherigen Rekursionslevel zurückkehrst.\n\n### Code Style\n- Die `// TODO implement`-Kommentare sind teilweise nicht mehr aktuell (weil du implementiert hast) und lenken eher ab; entferne oder ersetze sie durch passende Kommentare.\n- Kommentare sind teils unvollständig/abgebrochen (“Welche Bedingungen müssen gelten, das”); entweder vervollständigen oder weglassen, damit der Code leichter lesbar bleibt.\n\n\n# Exercise: sudoku\n\n### Correctness\n- `nofSolutions` ist nicht implementiert und liefert immer `0`, damit erfüllst du Anforderung 4 (Lösungen zählen) nicht.\n- In `solved(...)`: Wenn ein Feld bereits vorgegeben ist (`model.get(row,col) != 0`), rufst du `solved(model, fieldNr + 1)` auf, aber du gibst das Resultat nicht zurück. Dadurch läuft dein Code danach trotzdem in die Schleife und überschreibt vorgegebene Felder (und/oder liefert am Ende fälschlich `false`).\n- Die Vorgabe sagt: Wenn **keine** Lösung existiert, muss das `model` auf den **Initialzustand** zurückgesetzt werden. In deinem `solved(...)` wird bei Fehlschlag nicht garantiert, dass alle durch den Solver gesetzten Werte wieder entfernt sind (insbesondere weil der “vorgegebenes Feld”-Fall nicht korrekt beendet wird).\n\n### Suggestion\n- Für `nofSolutions`: Überlege dir dieselbe Rekursionsstruktur wie beim Lösen (nächstes Feld, Werte ausprobieren, Backtracking), aber statt “beim ersten Treffer true” sammelst du Treffer in einem Zähler. Den `max`-Parameter kannst du nutzen, um die Suche frühzeitig abzubrechen, sobald genug Lösungen gefunden wurden.\n- Für vorgegebene Felder in `solved(...)`: Sobald du erkennst, dass das Feld nicht 0 ist, solltest du den rekursiven Aufruf “durchreichen”, sodass der aktuelle Stack-Frame nicht weiterprobiert und das Feld nicht verändert.\n- Für “Model auf Initialzustand zurücksetzen”: Achte darauf, dass jedes Feld, das du in einem Rekursionsschritt testweise setzt, bei “kein Erfolg in diesem Zweig” wieder geleert wird, und dass du nicht versehentlich vorgegebene Felder anfasst.\n\n### Code Style\n- Du hast das Interface `SudokuModel#set` auf `boolean set(...)` geändert und in `SudokuModelImpl#set` dann immer `false` zurückgegeben. Das ist eine unnötige API-Änderung, die leicht zu Inkonsistenzen führt (und hier keinen Mehrwert bringt).\n- In `Sudoku.java` ist `main()` nicht `public static void main(String[] args)`. Das ist zwar nicht Teil der Solver-Aufgabe, aber so startet das Programm in einer normalen Java-Umgebung nicht über den Standard-Einstiegspunkt.\n\n\n# Exercise: queens\n\nLlm Evaluation ist für diese Aufgabe deaktiviert. Entferne die .llmignore Datei vom Package der Aufgabe.\n",
"status" : "SUCCESS"
},
"unitTest" : {
"tests" : [ {
"name" : "allZero()",
"status" : "PASSED",
"message" : null
}, {
"name" : "uselessStuff()",
"status" : "PASSED",
"message" : null
}, {
"name" : "random1()",
"status" : "FAILED",
"message" : "expected: <190> but was: <174>"
}, {
"name" : "random2()",
"status" : "FAILED",
"message" : "expected: <340> but was: <279>"
}, {
"name" : "random3()",
"status" : "FAILED",
"message" : "expected: <558> but was: <357>"
}, {
"name" : "boardIsValidAfterSolveN4()",
"status" : "FAILED",
"message" : "Board must contain exactly N queens ==> expected: <4> but was: <0>"
}, {
"name" : "boardIsValidAfterSolveN5()",
"status" : "FAILED",
"message" : "Board must contain exactly N queens ==> expected: <5> but was: <0>"
}, {
"name" : "boardIsValidAfterSolveN8()",
"status" : "FAILED",
"message" : "Board must contain exactly N queens ==> expected: <8> but was: <0>"
}, {
"name" : "boardSizeIsCorrectForN4()",
"status" : "PASSED",
"message" : null
}, {
"name" : "boardSizeIsCorrectForN8()",
"status" : "PASSED",
"message" : null
}, {
"name" : "countN1()",
"status" : "FAILED",
"message" : "N=1 has exactly 1 solution ==> expected: <1> but was: <0>"
}, {
"name" : "countN2()",
"status" : "PASSED",
"message" : null
}, {
"name" : "countN3()",
"status" : "PASSED",
"message" : null
}, {
"name" : "countN4()",
"status" : "FAILED",
"message" : "N=4 has exactly 2 solutions ==> expected: <2> but was: <0>"
}, {
"name" : "countN5()",
"status" : "FAILED",
"message" : "N=5 has exactly 10 solutions ==> expected: <10> but was: <0>"
}, {
"name" : "countN6()",
"status" : "FAILED",
"message" : "N=6 has exactly 4 solutions ==> expected: <4> but was: <0>"
}, {
"name" : "countN8()",
"status" : "FAILED",
"message" : "N=8 has exactly 92 solutions ==> expected: <92> but was: <0>"
}, {
"name" : "solveReturnsTrueForN1()",
"status" : "FAILED",
"message" : "N=1 has exactly one solution ==> expected: <true> but was: <false>"
}, {
"name" : "solveReturnsTrueForN4()",
"status" : "FAILED",
"message" : "N=4 has valid queen placements ==> expected: <true> but was: <false>"
}, {
"name" : "solveReturnsTrueForN8()",
"status" : "FAILED",
"message" : "N=8 has valid queen placements ==> expected: <true> but was: <false>"
}, {
"name" : "solveReturnsFalseForN2()",
"status" : "PASSED",
"message" : null
}, {
"name" : "solveReturnsFalseForN3()",
"status" : "PASSED",
"message" : null
} ]
}
}