Der Java-Klassendiagramm-Implementierungs-Aufgaben-Generator

By | 6.8.2017

Das mit dem Verstehen ist ja schön und gut, aber bei Sprachen – Programmiersprachen wie anderen – reicht es nicht, wenn man die grammatischen Kategorien kennt, man muss die Sprache auch anwenden können. In Bayern lernen die Schüler in Informatik in der 10. Klasse Gymnasium (im naturwissenschaftlich-technologischen Zweig) die Grundprinzipien es objektorientierten Modellierens und Programmierens. Mit den Prinzipien haben sie auch wenig Schwierigkeiten; Klassendiagramme kriegen sie einigermaßen hin – aber das Umsetzen der Diagramme in Programmcode macht vielen mehr Probleme.

Also habe ich mir vorgenommen, im nächsten Durchgang mehr zu pauken. Eine Doppelstunde nur Klassendiagramme implementieren. Und dann nochmal, wenn es nötig ist. Das kriegt man nämlich nur durch Übung rein. – Ob ich das dann wirklich so mache, hängt natürlich von der konkreten Klasse ab. Aber ich habe mir schon etwas vorbereitet, und zwar den Java-Klassendiagramm-Implementierungs-Aufgaben-Generator. So sieht er aus:

Benutzeroberfläche Programm

Wenn man auf den weißen Knopf kriegt, erzeugt und speichert das Programm zwei Textdateien. Die eine ist ein Klassendiagramm für eine zufällig erstellte Klasse, mit 1 zufällig ausgewählten Attribut, einem Standardkonstruktor und je einer getter- und setter-Methode für das Attribut:

|--------------------
| Raumschiff
|--------------------
| alter: int
|--------------------
| Raumschiff()
| getAlter(): int
| setAlter(int): void
|--------------------

Wenn man sparsam mit den Leerzeilen ist, kann man das in sechs kurzen Zeilen programmieren. Wenn die Schülerin das getan hat, importiert sie die zweite Datei, die das Programm erzeugt hat, in ihr Projekt. Diese Datei enthält den Code für eine weitere Java-Klasse, und zwar eine Testklasse, die überprüft, ob die Klasse auch semantisch richtig implementiert worden ist, also ob die Methoden auch das tun, was sie sollen, und ob das Attribut da ist, und ob die Datentypen und die Schreibung exakt mit dem Klassendiagramm übereinstimmen. Die Testklasse sieht so aus, auch wenn die Schülerin sich den Code nie anschauen muss:

import static org.junit.Assert.*;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
 
public class RaumschiffTest {
 
  Raumschiff testObject;
 
  public RaumschiffTest() {
  }
 
  @Before
  public void setUp() {
    testObject = new Raumschiff();
  }
 
  @After
  public void tearDown() {
    testObject=null;
  }
 
  @Test
  public void attributeUeberpruefen() {
    testObject.alter = 8;
  }
 
  @Test
  public void setAlterTest() {
    testObject.setAlter(40);
    assertEquals(40, testObject.alter);
    testObject.setAlter(11);
    assertEquals(11, testObject.alter);
    testObject.setAlter(31);
    assertEquals(31, testObject.alter);
  }
 
  @Test
  public void getAlterTest() {
    testObject.alter = -5;
    assertEquals(-5, testObject.getAlter());
    testObject.alter = 64;
    assertEquals(64, testObject.getAlter());
    testObject.alter = -17;
    assertEquals(-17, testObject.getAlter());
  }
 
}

Mit einem Mausklick startet man den Test, und herauskommt eine Anzeige, welche Tests bestanden wurde:

Java-Testergebnis

Dazu muss die von der Schülerin erstellte Klasse erst existieren, und war grammatisch fehlerfrei. Die Tests überprüfen nur, ob das Programm auch das tut, was es soll, nicht ob es überhaupt läuft – das sagt einem schon der Compiler eine Stufe zuvor.

Man kann sich auch Klassen mit zwei, drei oder vier Attributen erzeugen lassen. Wenn die Attribute nicht als private markiert sind, werden die Attribute überprüft und die getter/setter-Methoden anhand dieser Attribute überprüft – ansonsten wird die getter-Methode anhand der setter-Methode auf Richtigkeit getestet, und umgekehrt. Man auch auswählen, dass ein zweiter Konstruktor mit zu den Attributen passenden Argumenten erzeugt werden soll. Außerdem kann man noch ankreuzen, ob die neuen Objekte der Klasse bestimmte Startwerte für die Attribute haben sollen, die dann im Konstruktor festgelegt werden. Dann heißt es unter dem Klassendiagramm:

Der Wert des Attributs 'alter' soll am Anfang sein: 32

Die Werte für die Attribute werden ebenfalls zufällig ausgewählt. Attribute können vorerst nur vom Typ String, boolean, char, double, int sein. Die Testklasse wird jeweils unter Berücksichtigung all dieser Entscheidungen erstellt.

Das könnte man jetzt ausweiten und die Schüler selber Klassenbezeichner und Attribute auswählen lassen. Oder mit Referenzattributen arbeiten, dass also – für den Anfang – zwei Klassendiagramme erstellt werden, wobei das eine ein Referenz auf das zweite enthält.

Wen es stört, dass das so eine Art Liegestützen für Java sind, also eher sinnlose, wiederholende Übungen, der kann sich vielleicht daran erfreuen, dass die Schüler so an den Umgang mit Testklassen und Testverfahren herangeführt werden.

  • Download des .jar-Archivs. Vorsicht: Erzeugt im selben Verzeichnis die Textdateien im Format <Klasse>Test.java und <Klasse>Diagramm.txt und überschreibt vorhandene Dateien mit gleichem Namen ohne Rückfrage.
    • Erste Bugs gefunden, verbesserte Version von 2017-08-06, 19:50 Uhr
    • Neue Version vom 2017-08-07, 09:00 Uhr, etwas aufgeräumt im Code und assertEquals bei double verbesser

5 thoughts on “Der Java-Klassendiagramm-Implementierungs-Aufgaben-Generator

  1. Herr Rau Post author

    Gern geschehen – ich habe eben noch das .jar-Archiv aktualisiert, so dass jetzt auch die Quelldateien enthalten sind, so dass man die Klassenbezeichner und möglichen Attribute anpassen kann. (Auch wenn man dann sieht, wie inkonsistent das teilweise programmiert ist.)

  2. antje

    Vielen Dank! Sollte ich dieses Jahr eine 10. Klasse bekommen, probiere ich das wahrscheinlich mal aus. Mit den Testklassen hat man auch eine schöne Form der Selbstkontrolle, so dass man da gut differenzieren kann. Gerade in der 10. Klasse finde ich, dass die Leistungen der Schüler extrem auseinander gehen.

  3. Manuel Prochnow

    Hallo Herr Rau,

    das ist ein tolles Trainingstool um Diagramme in Code zu gießen.

    Beim ausprobieren ist mir aufgefallen, dass sie die Methode
    assertEquals(expected, actual)
    in ihren JUnit-Tests nutzen. Die ist jedoch deprecated. Falls es möglicht es schlage ich mal die Methode
    assertEquals(expected, actual, delta)
    vor. Ich habe das mal ausprobiert mit einem Attribut
    double delta = 0.000000000000001;
    damit laufen die Tests – wenn der Code ok ist – alle Grün.

    Würde mich über ein UpDate freuen.
    Parallel werde ich das mal selbst versuchen , das umzusetzen.

    LG Manuel

  4. Herr Rau Post author

    Danke für den Tipp, werde ich ergänzen. Mir war schon aufgefallen, dass man bei double den ganzen langen Wert abtippen muss, und dass ein kürzen auf die ersten 4 Stellen nicht geht – mit dem delta aber schon. Ich habe den Code von Hand geschrieben, statt den Testeditor von BlueJ zu nutzen, ich erinnere mich, der macht das automatisch mit einem delta.

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.