Datenstrukturen

Die vorliegenden Materialien wurden von Daniel Hoherz und André Tempel erstellt. Sollten andere Editoren die Materialien erstellt haben, werden diese explizit genannt.

Der Veranstalter Pyromania ist auf große Feuerwerkeffekte spezialisiert. Eine Stadt möchte ein Fest mit abschließendem Feuerwerk ausrichten und hat Pyromania engagiert, ein Feuerwerk auf einer Wasserplatform zu planen und durchzuführen.
Die Feuerwerksrakete werden in ein kleine Abschussschächte gesteckt, welche in einer langen Reihe miteinander verbunden sind. Die Raketen werden mit Kabeln mit einer Steuereinheit verbunden, welche ein vorher festgelegtes Programm zum Zünden der einzelnen Raketen ablaufen lässt.
Eine dieser Abschussvorrichtungen sieht zum Beispiel so aus:

KI-erzeugte Darstellung der Abschussvorrichtung

Wir betrachten zunächst nur eine Reihe der Anlage.
Eine Klasse Feuerwerk wird benötigt, welche unter anderem ein Attribut erhalten soll, in welchem gespeichert ist, was genau an welchem Platz in der Raketenreihe ist. Für ein konkretes Beispiel sollen diese sein: Rot, Grün, Grün und Blau.

Tauschen Sie sich mit Ihrem Sitznachbarn aus, wie Sie die Anlage algorithmisch speichern und verwalten könnten.

In der Informatik ist eine Datenstruktur ein Objekt, welches zur Speicherung und Organisation von Daten dient. Dabei handelt es sich um eine Struktur, weil die Daten in einer bestimmten Art und Weise angeordnet und verknüpft werden, um den Zugriff auf sie und ihre Verwaltung effizient zu ermöglichen. Wie bereits raus zu lesen ist, unterscheiden sich die Datenstrukturen wie sie strukturiert sind und welche Operationen es gibt, um einen Zugriff auf sie zu ermöglichen. So gibt es für verschieden Anwendungsbereich verschiedene Datenstrukturen, welche jeweils besser geeignet sind. Es werden die beiden Varianten statische Datenstruktur und dynamische Datenstruktur unterschieden.

Statische Datenstruktur Dynamische Datenstruktur
Beispiele int, boolean, char, String, double, Reihung, mehrdimensionale Reihung, … Stack, Queue, Dynamische Reihung…
Eigenschaften Feste Größe Größe der Datenstruktur und damit die Menge der speicherbaren Daten ist variabel, dynamisch

Die einfachste Form der Datenstrukturen haben wir bereits kennengelernt und vielfach genutzt – Variablen sogenannter primitiver Datentypen, wie z. B. integer, character, boolean…(Ein String ist kein primitiver Datentyp!).
Die Definition oben besagt, dass Datenstrukturen zur Speicherung von Daten dienen und diesen Sachverhalt haben die uns bisher bekannten Variablen erfüllt. Ebenso besagt die Definition, dass festgelegt wird, in welcher Art die Daten gespeichert werden. Auch diese wird bei Variablen festgelegt, indem gesagt wird, dass eine Variable von einem bestimmten Datentyp gespeichert wird. Darüber hinaus wird durch den Datentyp festgelegt, welche Operationen auf ihr möglich sind, womit dann auch der Zugriff geregelt wird.
Doch warum stehen die Variablen unter den statischen Datenstrukturen? Variablen sind statische Datenstrukturen, da ihre Größe, also wie viele Werte gespeichert werden können, immer gleich ist und nicht veränderlich sind.
Doch schauen wir uns mal andere statische Datenstrukturen an, die etwas mehr können, als eine Variable.

Rot Grün Grün Blau
0 1 2 3

Bei dieser Datenstruktur gibt es eine vorher festgelegte Anzahl an Feldern, in welche man eine Variable mit vorher festgelegtem Datentyp eintragen kann. Weiterhin sind die einzelnen Felder indiziert, beginnend mit dem Index 0.
Mit dieser Struktur sind einige Anforderungen an die Anlage deutlich einfacher umzusetzen. Die maximale Anzahl der Raketen ist direkt durch die vorher festgelegte Anzahl der Felder bekannt. Außerdem kann man die Felder der Reihe nach in einer beliebigen Formatierung ausgeben. Sucht man eine bestimmte Rakete, kann man die Felder schrittweise von vorne beginnend durchgehen und jeden Eintrag mit der gesuchten Farbe vergleichen. Wird ein Rakete enfernt, kann man diese suchen und aus dem entsprechenden Feld enfernen. Ebenso kann an eine freie Stelle direkt eine Rakete eingetragen werden, da man die Indizes einer freien Stelle suchen oder vorher speichern kann. Eine Erweiterung der Anlage ist ebenso möglich. Man erzeugt eine analoge Datenstruktur dieser Art, welche um die Anzahl der zusätzlichen Raketen größer ist, überträgt die bisherigen Raketen schrittweise in die neue Struktur und ergänzt schließlich die freien Felder mit den neuen Raketen.
Diese Art der Datenstruktur heißt eindimensionale Reihung bzw. eindimensionales Array, oder auch nur kurz Reihung bzw. Array.
Eine Reihung (Array/Feld) ist eine geordnete Sammlung von Werten. Die Werte können primitive Datentypen oder Objekte beliebiger anderer Klassen sein, aber alle Werte in einem Array müssen vom gleichen Typ sein.
Im Folgenden ist eine Übersicht über die Nutzung von Reihungen in Java gegeben.

Deklarieren einer Reihung
Wenn wir die oben abgebildete Reihung deklarieren wollen, dann wird das in Java so gemacht:

Deklarieren Erklärung
String[] test; String [ ] test ;
Datentyp der Objekte in der Reihung Klammern Name des Arrays Ende der Anweisung

Initialisieren einer Reihung
Bisher wurde nur Speicherplatz für die Reihung test reserviert, in welche nur Zeichenketten gespeichert werden dürfen. Damit der Computer weiß, wie groß die Reihung sein soll, muss man sie initialisieren:

Initialisieren Erklärung
test=new String[4]; test = new String[4]
Name der Reihung Wertzuweisung Konstruktor einer Reihung und Angabe der Größe

Jetzt existiert eine leere Reihung der Größe 4, in welcher Zeichenketten gespeichert werden dürfen. Aktuell ist die Reihung aber leer. Das bedeutet, dass an allen Positionen null eingetragen ist.

test: null null null null
Index: 0 1 2 3

Man kann auch beide Schritte gleichzeitig machen, wenn die Größe der Reihung direkt angegeben werden soll:

Deklarieren + Initialisieren Erklärung
String[] test=new String[4]; String[] test = new String[4]
Deklarieren Wertzuweisung Initialisieren

Werte in einer Reihung speichern
Nun sollen die Raketen aus dem Einstiegsbeispiel in unserer Reihung gespeichert werden. Wir starten mit der ersten Rakete, „Rot“ am Index 0:

Speichern Erklärung
test[0] = „Rot“; test [0] = „Rot“
Name der Reihung Index, der angesprochen werden soll Wertzuweisung Neuer Wert, hier ein String

Man kann auch direkt Deklarieren, Initialisieren und Werte zuweisen, sollte man dies wollen bzw. können:

Alles zusammen Erklärung
String[] test = {„Rot“,“Grün“,“Grün“,“Blau“}; String[] test = {„Rot“,“Grün“,“Grün“,“Blau“}
Deklarieren Wertzuweisung Werte direkt speichern

Werte aus Reihung auslesen
Wenn eine Reihung vorhanden ist und man sich für deren Inhalte interessiert, kann man auch die gespeicherten Objekte abfragen. Man kann so entweder Einträge der Reihung in anderen Variablen speichern oder sich einfach einen Wert ausgeben lassen. Mit einer Schleife kann man sich auch alle Elemente der Reihung ausgeben:

Ein Wert aus test in einer Variablen speichern Erklärung
String s;
s = test[1];
s = test[1]
Wo gespeichert wird Der Wert am Index 1, hier „Grün“, wird zurückgegeben

Einen Wert aus test ausgeben Erklärung
System.out.print(test[4]); System.out.print(…) test[4]
Etwas auf der Konsole anzeigen Der Wert am Index 4, hier „Blau“, wird zurückgegeben

Alle Werte in test ausgeben Erklärung
for(int i=0; i<4; i++) {
System.out.print(test[i]);
}
for(int i=0; i<4; i++) System.out.print(…) test[i]
Schleife, die 4-mal durchläuft Etwas auf der Konsole anzeigen Der Wert am aktuellen Index i, wird zurückgegeben

Länge der Reihung angeben
Man kann sich auch die Länge einer Reihung zurückgeben lassen:

Länge von test nutzen Erklärung
int a = test.length; int a = test.length
Ganzzahlvariable a deklarieren und einen Wert zuweisen Länge von test, hier 4, wird zurückgegeben

Dies kann man nutzen, um die gesamte Reihung wie weiter oben zu durchlaufen, wenn deren Länge nicht bekannt ist.

Alle Werte in test ausgeben Erklärung
for(int i=0; i<test.length; i++) {
System.out.print(test[i]);
}
for(int i=0; i<test.length; i++) System.out.print(test[i])
Schleife, die so oft durchläuft, wie die Reihe groß ist Auf der Konsole den Wert von test am aktuellen Index ausgeben

Achtung: Wenn ein negativer Index oder ein Index, der größer ist, als das letzte Element der Reihung, eingegeben wird, dann wird eine IndexOutOfBoundsException ausgelöst, die angibt, dass man den Index-Bereich/die Größe der Reihung verlassen hat.

  1. Um zunächst ein wenig den Umgang mit Reihungen kennenzulernen sind im folgenden die wichtigsten Informationen zu Reihungen in Java an konkreten Beispielen vorgegeben. Nutzen Sie schrittweise die Erklärungen (oben), um die folgenden Aufgaben zu bearbeiten.
  2. Deklarieren und initialisieren Sie auf je zwei verschiedene Weisen die folgenden Reihungen in der main-Methode in Java.

    • eine Zeichenkettenreihung mit den Werten haus, auto, baum, pWanze, katze, maus
    • eine Ganzzahlreihung mit den Werten 4, 32, -1, 79, 13
    • eine char-Reihung mit den Werten a, b, c, d, e, f, g

    Ersetzen Sie in jeder Ihrer Reihungen einen beliebigen Wert durch einen anderen.

    Lassen Sie sich nacheinander die Werte einer der drei Reihungen vollständig ausgeben und zwar in mindestens drei Varianten:

    • Ein Wert pro Zeile,
    • Alle Werte in einer Zeile,
    • Es wird nur jeder zweite Wert ausgeben,
    • Alle Werte sollen rückwärts, also von hinten nach vorne, ausgegeben werden.

  1. Die Klasse Feuerwerk soll zunächst wie unten abgebildet umgesetzt werden.
    Das Attribut anlage ist eine Zeichenkettenreihung, welche die Raketen in Form von Zeichenketten (die jeweilige Farbe) speichern soll. Das Attribut laenge ist die Länge der Anlage.
    Dem Konstruktor wird eine Zeichenkettenreihung übergeben, welche als anlage gespeichert werden soll. Das Attribut laenge soll vom Konstruktor auf die Länge von anlage gesetzt werden. Die get-Operation sollen die Länge der Anlage, eine Rakete an einer bestimmten Stelle und die gesamte Anlage zurückgeben.
    Die set-Operation soll an den übergebenen Index die übergebene Rakete platzieren.

    Klassenkarte der Klasse Feuerwerk

    Entscheiden Sie, ob Sie die Basis- oder die Challenge-Variante umsetzen wollen. Sie können auch jederzeit zwischen diesen wechseln.

  2. Kopieren Sie sich die Klassen Feuerwerk und FeuerwerkTest heruntern und starten Sie es.

    Führen Sie die Klasse FeuerwerkTest aus.
    Erläutern Sie die Funktionsweise der Operationen public Feuerwerk(String[] s), public int getLaenge() und der Anweisungen in der Klasse FeuerwerkTest.

    Die weiteren in der Klassenkarte abgebildeten Operationen haben die folgende Funktionsweise:

    • getRakete soll die am übergebenen Index a gespeicherte Rakete zurückgeben.
    • getAnlage soll die gesamte Anlage zurückgeben.
    • setRakete soll die Rakete am übergebenen Index b mit der Zeichenkette r überschreiben.
    • (Ergänzung) showAnlage soll die komplette Anlage als Zeichenkettenreihung zurückgegeben.

    Schauen Sie sich die noch nicht gefüllten Operationen in der Klasse Feuerwerk an und erläutern Sie die einzelnen Elemente der Methodenköpfe. Gehen Sie hierbei insbesondere auf Übergabeparameter und Rückgabewerte ein.

    Vervollständigen Sie die Operationen getRakete, getAnlage und setRakete.
    Testen Sie die get-Operationen.
    Ersetzen Sie die blaue Rakete durch eine weiße Rakete.

    Eine weitere get-Operation soll ergänzt werden. Die Operation getRakete(String c) erhält eine Farbe als Zeichenkette übergeben und soll den ersten Index zurückgeben, an dem sich eine Rakete der gesuchten Farbe befindet. Nun wird es zwei Operationen getRakete geben, die sich im Übergabeparameter unterscheiden. Der Computer wählt, je nach Datentyp des Übergabeparameters die entsprechende Operation aus. Das nennt man Überladen von Operationen.
    Implementieren Sie die neue Operation getRakete.

    Die Operation hatFarbe soll überprüfen, ob eine übergebene Farbe in der Reihung anlage enthalten ist und in diesem Fall true zurückgeben, anderenfalls false.
    Implementieren Sie die Operation hatFarbe.

    Die Operation changeRakete(int i1, int i2) soll in der Reihung anlage die Raketen an den beiden übergebenen Positionen tauschen.
    Implementieren Sie die Operation changeRakete.

    Nun soll es die Möglichkeit geben, die Flughöhe der Raketen der Reihung anlage zu speichern. Hierfür erhält die Klasse Feuerwerk eine zweites Attribut hoehe vom Datentyp Ganzzahlreihung.
    Ergänzen Sie Ihre Klasse Feuerwerk um das Attribut hoehe. Verändern Sie den bisherigen Konstruktor so, dass er die Werte in hoehe auf 0 setzt.
    Implementieren Sie einen zweiten Konstruktor, dem zusätzlich zur Zeichenkettenreihung eine Ganzzahlreihung übergeben wird, welche unter dem Attribut hoehe gespeichert werden soll.
    Erstellen Sie nun ein Objekt der Klasse Feuerwerk mit den Raketen Rot, Gruen, Blau, Rot und den Flughöhen 100, 80, 120, 90.

    Implementieren Sie eine Operation minHoehe, welche den Index des kleinsten Wertes der Flughöhe ermittelt und zurückgibt. Machen Sie dieses nochmal für maxHoehe.
    Zusatz: Implementieren Sie eine Operation ordneHöhe, welche den kleinsten Wert der Flughöhe an den Index 0 tauscht.

    Optimieren Sie Ihre Operationen, sodass nicht sinnvolle Eingaben abgefangen werden.
    Beispielsweise könnte man bei getRakete(int a) einen Index eingeben, den es nicht gibt.

    Implementieren Sie die Klasse Feuerwerk wie oben beschrieben.

    Erstellen Sie eine Testklasse, in welcher Sie ein Objekt der Klasse Feuerwerk mit den Raketen Rot, Gruen, Blau, Rot anlegen.
    Testen Sie die get-Operationen.
    Ersetzen Sie die blaue Rakete durch eine weiße Rakete.

    Eine weitere get-Operation soll ergänzt werden. Die Operation getRakete(String c) erhält eine Farbe als Zeichenkette übergeben und soll den ersten Index zurückgeben, an dem sich eine Rakete der gesuchten Farbe befindet. Nun wird es zwei Operationen getRakete geben, die sich im Übergabeparameter unterscheiden. Der Computer wählt, je nach Datentyp des Übergabeparameters die entsprechende Operation aus. Das nennt man Überladen von Operationen.
    Implementieren Sie die neue Operation getRakete.

    Die Operation hatFarbe soll überprüfen, ob eine übergebene Farbe in der Reihung anlage enthalten ist und in diesem Fall true zurückgeben, anderenfalls false.
    Implementieren Sie die Operation hatFarbe.

    Die Operation changeRakete(int i1, int i2) soll in der Reihung anlage die Raketen an den beiden übergebenen Positionen tauschen.
    Implementieren Sie die Operation changeRakete.

    Nun soll es die Möglichkeit geben, die Flughöhe der Raketen der Reihung anlage zu speichern. Hierfür erhält die Klasse Feuerwerk eine zweites Attribut hoehe vom Datentyp Ganzzahlreihung.
    Ergänzen Sie Ihre Klasse Feuerwerk um das Attribut hoehe. Verändern Sie den bisherigen Konstruktor so, dass er die Werte in hoehe auf 0 setzt.
    Implementieren Sie einen zweiten Konstruktor, dem zusätzlich zur Zeichenkettenreihung eine Ganzzahlreihung übergeben wird, welche unter dem Attribut hoehe gespeichert werden soll.
    Erstellen Sie nun ein Objekt der Klasse Feuerwerk mit den Raketen Rot, Gruen, Blau, Rot und den Flughöhen 100, 80, 120, 90.

    Implementieren Sie eine Operation minHoehe, welche den Index des kleinsten Wertes der Flughöhe ermittelt und zurückgibt. Machen Sie dieses nochmal für maxHoehe.
    Zusatz: Implementieren Sie eine Operation ordneHöhe, welche den kleinsten Wert der Flughöhe an den Index 0 tauscht.

  1. Vergleichen Sie in einer eigenen Testklasse die beiden folgenden Algorithmen:
    int[] zahlen = {1,-2,3,-4,5,-6,7,-8,9,-10};
    for (int i = 0; i < zahlen.length; i++) {
        print(zahlen[i] + " ");
    }
    
    
    int[] zahlen = {1,-2,3,-4,5,-6,7,-8,9,-10};
    for (int zahl : zahlen) {
        print(zahl + " ");
    }
    
    
    Die linke Variante ist eine bekannte for-Schleife. Die rechte Variante ist eine erweiterte for-Schleife, auch for-each-Schleife genannt. Diese kann man alternativ zu einer for-Schleife für alle Arrays nutzen.
  1. Ein Objekt der Klasse Color ist eine Farbe in RGB-Codierung. Hierbei werden die Intensitäten der Grundfarben Rot, Grün und Blau in jeweils ganzzahligen Werten im Bereich von 0 bis 255 angegeben. Beispiele für konkrete Farben finden Sie unten.

    Farbe HTML-Name RGB-Dezimalcodierung
    Weiß (255,255,255)
    Schwarz (0,0,0)
    Rot (255,0,0)
    Limette (0,255,0)
    Blau (0,0,255)
    Gelb (255,255,0)
    Cyan (0,255,255)
    Magenta (255,0,255)
    Grün (0,128,0)
    Lila (128,0,128)
    Beispiele für die RGB-Codierung von Farben

    Die Klasse Feuerwerk wird um die Klasse Color und andere Funktionalitäten erweitert, siehe unten. Der Datentyp der Reihung anlage wird dadurch von Zeichenkette zu Color. In einer Challenge-Variante wird zusätzlich noch eine Klasse Rakete genutzt, wodurch der Datentyp der Reihung anlage von Zeichenkette zu Rakete wird.
    Entscheiden Sie sich zu Beginn dieser Aufgabe für eine der beiden Varianten. Die Klasse Color liegt bereits vor und kann entspechend genutzt werden.

  2. Klassenkarte der Klassen Feuerwerk und Color

    Verändern Sie Ihre bisherige Klasse Feuerwerk entsprechend der neuen Situation.

    Ist ein Platz der Reihung anlage nicht besetzt, wird eine Rakete mit der Farbe Schwarz mit Flughöhe 0 an die freie Stelle gesetzt.
    Verändern Sie die Konstruktoren entsprechend.
    Erstellen Sie ein neues Objekt der Klasse Feuerwerk und belegen Sie die Reihung anlage mit Raketen der Farben Rot, Blau, freier Platz, Grün, Blau, in der angegebenen Reihenfolge.

    Die Operation setRakete soll nun eine Rakete an einen bestimmten Platz setzen, wenn dieser Platz nicht besetzt ist.
    Verändern Sie die Operation setRakete nach diesen Vorgaben.
    Testen Sie die Operation, indem Sie eine weiße Rakete an die freie Stelle setzen.

    Die Operation zuenden der Klasse Feuerwerk erhält eine Reihung aus Farben als Übergabeparameter und soll zählen, wie viele Raketen der jeweiligen Farben in der Reihung anlage enthalten sind und deren Anzahlen in einer Ganzzahlreihung zurückgeben.
    Implementieren Sie die Operation zuenden.
    Testen Sie die Operation für rote und blaue Raketen.

    Klassenkarte der Klassen Feuerwerk und Color

    Implementieren Sie die Klasse Rakete und nutzen Sie die Klasse Color entsprechend.

    Verändern Sie Ihre bisherige Klasse Feuerwerk entsprechend der neuen Situation.

    Ist ein Platz der Reihung anlage nicht besetzt, wird eine Rakete mit der Farbe Schwarz und 0 für die anderen Attributswerte an die freie Stelle gesetzt.
    Verändern Sie den Konstruktor entsprechend.
    Erstellen Sie ein neues Objekt der Klasse Feuerwerk und belegen Sie die die Reihung anlage mit Raketen der Farben Rot, Blau, freier Platz, Grün, Blau, in der angegebenen Reihenfolge.
    Das Attribut laenge soll einen beliebigen Wert zwischen 10.0 und 25.0 haben, zdauer zwischen 1.0 und 3.0 und hoehe zwischen 20 und 60.

    Die Operation setRakete soll nun ein Objekt der Klasse Rakete an einen bestimmten Platz setzen, wenn dieser Platz nicht besetzt ist. Ist der Platz jedoch besetzt, soll die neue Rakete an den darauf folgenden Platz gesetzt und die restlichen Plätze nach hinten geschoben werden. Gegebenenfalls muss die letzte Rakete enfernt werden.
    Verändern Sie die Operation setRakete nach diesen Vorgaben.
    Testen Sie die Operation, indem Sie eine weiße Rakete am Index 1 einfügen.

    Die Operation zuenden der Klasse Feuerwerk erhält eine Reihung aus Farben und eine Ganzzahl als Übergabeparameter. Sie soll zählen, wie viele Raketen der jeweiligen Farben in der Reihung anlage enthalten sind und gleichzeitig mindestens die übergebene Flughöhe erreichen und deren Anzahlen in einer Ganzzahlreihung zurückgeben.
    Implementieren Sie die Operation zuenden.
    Testen Sie die Operation für rote und blaue Raketen und einer Flughöhe von 40.

  1. Nun soll es um eine Wetterstation gehen.
    Die Wetterstation hat für 14 Tage die folgenden Temperaturen aufgezeichnet.
    Tag 1 2 3 4 5 6 7 8 9 10 11 12 13 14
    Temperatur in °C 12 14 9 12 15 16 15 15 11 8 13 13 15 12
  2. Erstellen Sie eine Klasse Wetterstation, welche ein Attiribut temperaturen in Form einer Ganzzahlreihung hat.
    Der Konstruktor initialisiert die Reihung temperaturen in der oben angegebenen Form.
    Außerdem gibt es eine Operation ausgabe zum Ausgeben aller Werte in temperaturen.
    Testen Sie anschließend mit Hilfe einer Test-Klasse Ihre Implementierung.

    Entwickeln Sie Operation max (min), um die maximale (und minimale) Temperatur zu ermitteln und diese in geeigneter Form auszugeben.
    Testen Sie anschließend mit Hilfe Ihrer Test-Klasse Ihre Implementierung.

    Entwickeln Sie Operation max2 (min2), um die maximale (und minimale) Temperatur und den dazugehörigen Tag zu ermitteln und diese in Form einer Reihung der Länge 2 zurückzugeben.
    Testen Sie anschließend mit Hilfe Ihrer Test-Klasse Ihre Implementierung.

    Entwickeln Sie eine Operation avg, welche die Durchschnittstemperatur der zwei Wochen bestimmt und zurückgibt.
    Berechnen Sie den Durchschnittswert noch einmal selbst und vergleichen Sie die beiden Ergebnisse.
    Erläutern Sie, wie eventuelle Unterschiede zu Stande kommen und passen Sie Ihre Klasse Wetterstation geeignet an.

    Die Operation erweiterteInfos soll eine Reihung temperaturen, welche übergeben wird und eine unbekannte Anzahl von Tagestemperaturen beinhaltet, um drei Elemente erweitern, die vorhandenen Temperaturen übertragen, die Durchschnittstemperatur aller Tage an den ersten neuen Platz setzen. An die beiden anderen Plätze soll zuerst die Anzahl der Tage eingetragen werden, die mindestens 3° C unter der Durchschnittstemperatur und an die letzte Stelle die Anzahl der Tage, die mindestens 3° C über der Durchschnittstemperatur lagen. Die so entstandene Ganzzahlreihung soll zurückgegeben werden. Die Operation durchschnitt(int[] t), welche das arithmetische Mittel aller in t gespeicherten Zahlen als gerundete Ganzzahl bestimmt und zurückgibt, kann genutzt werden. Ein erster Entwurf der Operation erweiterteInfos ist im unten abgebildeten Struktogramm zu sehen.

    Klassenkarte der Klasse Feuerwerk

    Analysieren Sie die Funktionsweise des Algorithmus, wenn die Reihung 9, 13, 8, 10, 10, 5, 6 übergeben wird.
    Geben Sie die Reihung neu an, die am Schluss zurückgegeben wird.

    Verändern Sie das Struktogramm, sodass die Operation wie gewünscht funktioniert.

  1. (eA) Die folgenden Aufgaben beziehen sich auf das Adventure-Szenario. Wir hatten zuletzt den Magier hinzugefügt.

    Sie werden im Folgenden primär die Klassen Held, Goblin und Magier benötigen. Der letzten Stand wird Ihnen in der Online-IDE zur Verfügung gestellt oder Sie arbeiten mit Ihrer Version weiter.

  2. Ein Magier soll zusätzlich das Attribut zauberbuch in Form eines String-Array haben und alle Magier sollen mit den Zaubersprüchen Fliegen, Feuerball und Blitz starten. Das Zauberbuch muss also mindestens die Länge 3 haben.
    Erweitern Sie Ihren Implementierung geeignet und testen Sie diese.

    Implementieren Sie für die Klasse Magier eine Operation getZauber, welche alle Zauber des Zauberbuchs auf der Konsole ausgibt und testen Sie Ihre Operation.

    Ihr erstellter Magier soll anstelle des Zaubers Feuerball den Zauber Feuerblitz gelernt haben.
    Implementieren Sie eine Operation setZauber(int index, String zauber), um an einer bestimmten Stelle (index) einen neuen Zauber (zauber) einzutragen.

    Die Operation changeZauber(int i1, int i2) soll im Zauberbuch die beiden Zauber an den übergebenen Stellen tauschen.
    Implementieren Sie diese Operation.

    Der Magier hat nun eine Tasche voller Zaubertränke und jeder Zaubertrank wird nur durch einen ganzzahligen Wert (int) repräsentiert (s. Ausschnitt des Klassendiagramm neben den Aufgabenteilen), um den er heilt. Das Zauberbuch wurde bereits in der vorherigen Aufgabe umgesetzt.
    Ergänzen Sie zunächst das Attribut in Form einer Reihung zaubertraenke vom Inhaltstyp int und initialisieren Sie diese mit den Werten: {42, 7, 1, 17, 19}

    Implementieren Sie eine Operation minZaubertraenke, welche den Index des kleinsten Wertes ermittelt und zurückgibt. Machen Sie dieses nochmal für maxZaubertraenke.
    Implementieren Sie eine Operation ordneZaubertraenke(), welche den kleinsten Wert der Reihung an den Index 0 tauscht.

    Es soll eine neue Klasse Zauber erstellt werden. Ein Zauber verstärkt durch das Attribut staerke den Schaden beim Zaubern.
    Implementieren Sie diese Anforderung und passen Sie gegebenenfalls die Operationen und Attribute der Klasse Magier an.

Die Modellierung unserer Raketenreihung wird nun erweitert, sodass auch mehrere Reihen möglich sind (siehe Abbildung unten).
Wir gehen davon aus, dass in jeder Zeile gleich viele Raketen platziert werden können. Eine Beispielbelegung würde wie folgt aussehen:

0 1 2 3
0 Rot Grün Grün Blau
1 Rot Grün Grün Blau
2 Rot Grün Grün Blau
3 Rot Grün Grün Blau
4 Rot Grün Grün Blau
5 Rot Grün Grün Blau

Deklarieren einer zweidimensionalen Reihung
Wenn wir die oben abgebildete zweidimensionale Reihung deklarieren wollen, dann wird das in Java so gemacht:

Deklarieren Erklärung
String[][] test; String [ ][ ] test ;
Datentyp der Objekte in der Reihung Klammern Name des Arrays Ende der Anweisung

Initialisieren einer zweidimensionalen Reihung
Bisher wurde nur Speicherplatz für die 2d-Reihung test reserviert, in welche nur Zeichenketten gespeichert werden dürfen. Damit der Computer weiß, wie groß die 2d-Reihung sein soll, muss man sie initialisieren:

Initialisieren Erklärung
test=new String[6][4]; test = new String[6][4]
Name der Reihung Wertzuweisung Konstruktor einer Reihung und Angabe der Größe --> Zeilen zuerst, Spalten später

Jetzt existiert eine leere 2d-Reihung mit 6 Zeilen und 4 Spalten, in welcher Zeichenketten gespeichert werden dürfen. Aktuell ist die 2d-Reihung aber leer. Das bedeutet, dass an allen Positionen null eingetragen ist.

0 1 2 3
0 null null null null
1 null null null null
2 null null null null
3 null null null null
4 null null null null
5 null null null null

Man kann auch beide Schritte gleichzeitig machen, wenn die Größe der 2d-Reihung direkt angegeben werden soll:

Deklarieren + Initialisieren Erklärung
String[][] test=new String[6][4]; String[][] test = new String[6][4]
Deklarieren Wertzuweisung Initialisieren

Werte in einer 2d-Reihung speichern
Nun sollen die Raketen aus dem Einstiegsbeispiel in unserer 2d-Reihung gespeichert werden. Wir starten mit der ersten Rakete, "Rot" am Index (0,0) und einer grünen woanders:

Speichern Erklärung
test[0][0] = "Rot"; test [0][0] = "Rot"
Name der Reihung Index, der angesprochen werden soll --> Zeile 0 und Spalte 0 Wertzuweisung Neuer Wert, hier ein String

Speichern Erklärung
test[3][1] = "Grün"; test [3][1] = "Grün"
Name der Reihung Index, der angesprochen werden soll --> Zeile 3 und Spalte 1 Wertzuweisung Neuer Wert, hier ein String

Man kann auch direkt Deklarieren, Initialisieren und Werte zuweisen, sollte man dies wollen bzw. können. Wir machen das, und auch die folgenden Beispiele, für eine kleinere 2d-Reihung als die im Einstiegsbeispiel:

0 1
0 Rot Grün
1 Blau Rot
2 Weiß Rot
3 Rot Weiß

Alles zusammen Erklärung
String[][] test = {{"Rot","Grün"}, {"Blau","Rot"},{"Weiß","Rot"}, {"Rot","Weiß"}}; String[][] test = {{"Rot","Grün"}, {"Blau","Rot"},{"Weiß","Rot"}, {"Rot","Weiß"}};
Deklarieren Wertzuweisung Werte direkt speichern

Werte aus 2d-Reihung auslesen
Wenn eine 2d-Reihung vorhanden ist und man sich für deren Inhalte interessiert, kann man auch die gespeicherten Objekte abfragen. Man kann so entweder Einträge der 2d-Reihung in anderen Variablen speichern oder sich einfach einen Wert ausgeben lassen. Mit einer Schleife kann man sich auch alle Elemente der Reihung ausgeben. Mit einer geschachtelten Schleife kann man sich auch alle Elemente der Reihung ausgeben:

Ein Wert aus test in einer Variablen speichern Erklärung
String s;
s = test[1][0];
s = test[1][0]
Wo gespeichert wird Der Wert am Index (1,0), hier "Blau", wird zurückgegeben

Einen Wert aus test ausgeben Erklärung
print(test[0][1]); print(...) test[0][1]
Etwas auf der Konsole anzeigen Der Wert am Index (0,1), hier "Grün", wird zurückgegeben

Alle Werte in test ausgeben Erklärung
for(int i=0; i<4; i++) {
for(int j = 0; j<2;j++){
print(test[i][j]);
}
}
for(int i=0; i<4; i++) for(int j = 0; j<2;j++) print(test[i][j])
Äußere Schleife für die Zeilen Innere Schleife für die Spalten Der Wert am aktuellen Index (i,j), wird zurückgegeben

Länge der Reihung angeben
Man kann sich auch die Anzahl der Zeilen und Spalten einer 2d-Reihung zurückgeben lassen:

Zeilenanzahl von test nutzen Erklärung
int a = test.length; int a = test.length
Ganzzahlvariable a deklarieren und einen Wert zuweisen Länge von test, hier 4, wird zurückgegeben

Spaltenanzahl von test nutzen Erklärung
int a = test[0].length; int a = test[0].length
Ganzzahlvariable a deklarieren und einen Wert zuweisen Länge von test, hier 4, wird zurückgegeben

Dies kann man nutzen, um die gesamte 2d-Reihung wie weiter oben zu durchlaufen, wenn deren Länge nicht bekannt ist.

Alle Werte in test ausgeben Erklärung
for(int i=0; i<test.length; i++) {
for(int j = 0; j<test[0].length;j++){
print(test[i][j]);
}
}
for(int i=0; i<test.length; i++) for(int j = 0; j<test[0].length;j++) print(test[i][j])
Äußere Schleife für die Zeilen Innere Schleife für die Spalten Der Wert am aktuellen Index (i,j), wird zurückgegeben

Achtung: Wenn ein negativer Index oder ein Index, der größer ist, als das letzte Element der 2d-Reihung, eingegeben wird, dann wird eine IndexOutOfBoundsException ausgelöst, die angibt, dass man den Index-Bereich/die Größe der Reihung verlassen hat.

  1. Um zunächst ein wenig den Umgang mit 2d-Reihungen kennenzulernen sind oben die wichtigsten Informationen zu 2d-Reihungen in Java an konkreten Beispielen vorgegeben. Nutzen Sie schrittweise die Erklärungen (oben), um die folgenden Aufgaben zu bearbeiten.
  2. Deklarieren und initialisieren Sie auf je zwei verschiedene Weisen die folgenden Reihungen in einer Klasse Array2DTest in Java.

    • eine 2d- Zeichenkettenreihung mit den Zeilen:
      • haus, auto, baum
      • pflanze, katze, maus
    • eine Ganzzahlreihung mit den Zeilen:
      • 4 , 32
      • -1, 79
      • 13, 0
    • eine char-Reihung mit den Zeilen:
      • a, b, c
      • d, e, f
      • g, h, i

    Ersetzen Sie in jeder Ihrer Reihungen einen beliebigen Wert durch einen anderen.

    Lassen Sie sich nacheinander die Werte einer der drei Reihungen vollständig ausgeben und zwar in mindestens drei Varianten:

    • In einer einzigen Zeile,
    • Jede Zeil der Reihung ist auch eine eigene Zeile auf der Konsole,
    • Es wird nur jeder zweite Wert ausgeben.

  1. Die Klasse Feuerwerk soll zunächst wie rechts abgebildet umgesetzt werden.
    Das Attribut anlage ist eine zweidimensionale Reihung vom Inhaltstyp Zeichenkette, welche die Raketen in Form von Zeichenketten (die jeweilige Farbe) speichern soll. Das Attribut dim ist eine Reihung vom Inhaltstyp Ganzzahl und der Größe 2, in der an der ersten Stelle die Zeilen- und an der zweiten die Spaltenanzahl der Anlage steht.

    Klassenkarte der Klasse Feuerwerk

    Entscheiden Sie, ob Sie die Basis- oder die Challenge-Variante umsetzen wollen. Sie können auch jederzeit zwischen diesen wechseln.

  2. Ihnen wurde über die Online IDE ein Framework Feuerwerk2Dim zur Verfügung gestellt.

    Führen Sie die Klasse FeuerwerkTest aus.
    Erläutern Sie die Funktionsweise der Operationen public Feuerwerk(String[][] s), public int[] getDim() und der Anweisungen in der Klasse FeuerwerkTest.

    Die weiteren in der Klassenkarte abgebildeten Operationen haben die folgende Funktionsweise:

    • getRakete soll die an der übergebenen Zeile a und übergebenen Spalte b gespeicherte Rakete zurückgeben.
    • showAnlage soll die gesamte Anlage auf der Konsole ausgeben.
    • setRakete soll die Rakete an der übergebenen Zeile a und übergebenen Spalte b mit der Zeichenkette r überschreiben.

    Schauen Sie sich die noch nicht gefüllten Operationen in der Klasse Feuerwerk an und erläutern Sie die einzelnen Elemente der Methodenköpfe. Gehen Sie hierbei insbesondere auf Übergabeparameter und Rückgabewerte ein.

    Vervollständigen Sie die Operationen getRakete, showAnlage und setRakete.
    Testen Sie die get-Operationen und showAnlage.
    Ersetzen Sie die blaue Rakete durch eine weiße Rakete.

    Eine weitere get-Operation soll ergänzt werden. Die Operation getRakete(String c) erhält eine Farbe als Zeichenkette übergeben und soll die erste Stelle zurückgeben, an dem sich eine Rakete der gesuchten Farbe befindet.
    Implementieren Sie die neue Operation getRakete.

    Die Operation hatFarbe soll überprüfen, ob eine übergebene Farbe in der Reihung anlage enthalten ist und in diesem Fall true zurückgeben, anderenfalls false.
    Implementieren Sie die Operation hatFarbe.

    Die Operation changeRakete(int i1, int i2, int i3, int i4) soll in der Reihung anlage die Raketen an den beiden übergebenen Positionen (i1,i2) und (i3,i4) tauschen.
    Implementieren Sie die Operation changeRakete.

    Nun soll es die Möglichkeit geben, die Flughöhe der Raketen der Reihung anlage zu speichern. Hierfür erhält die Klasse Feuerwerk ein zweites Attribut hoehe in Form einer zweidimensionalen Reihung vom Inhaltstyp Ganzzahl.
    Ergänzen Sie Ihre Klasse Feuerwerk um das Attribut hoehe. Verändern Sie den bisherigen Konstruktor so, dass er die Werte in hoehe auf 0 setzt.
    Implementieren Sie einen zweiten Konstruktor, dem zusätzlich zur Zeichenkettenreihung eine zweidimensionalen Reihung vom Inhaltstyp Ganzzahl übergeben wird, welche unter dem Attribut hoehe gespeichert werden soll.
    Erstellen Sie nun ein Objekt der Klasse Feuerwerk mit den Raketen wie im Einstieg des Abschnitts und zufälligen Flughöhen zwischen mindestens 50m und maximal 120m.

    Implementieren Sie eine Operation minHoehe, welche das Indexpaar des kleinsten Wertes der Flughöhe ermittelt und zurückgibt. Machen Sie dieses nochmal für maxHoehe.
    Implementieren Sie eine Operation ordneHöhe, welche den kleinsten Wert der Flughöhe an den Index (0,0) tauscht.

    Optimieren Sie Ihre Operationen, sodass nicht sinnvolle Eingaben abgefangen werden.
    Beispielsweise könnte man bei getRakete(int a, int b) einen Index eingeben, den es nicht gibt.

    Die Klasse Feuerwerk soll zunächst wie oben abgebildet umgesetzt werden.
    Das Attribut anlage ist eine zweidimensionale Reihung vom Inhaltstyp Zeichenkette, welche die Raketen in Form von Zeichenketten (die jeweilige Farbe) speichern soll. Das Attribut dim ist eine Reihung vom Inhaltstyp Ganzzahl und der Größe 2, in der an der ersten Stelle die Zeilen- und an der zweiten die Spaltenanzahl der Anlage steht.
    Dem Konstruktor wird eine zweidimensionale Reihung vom Inhaltstyp Zeichenkette übergeben, welche als anlage gespeichert werden soll. Beim Aufrufen des Konstruktors sollen die Zeilen- und Spaltenanzahl der übergebenen Reihung bestimmt und in das Attribut dim gespeichert werden. Die get-Operation sollen die Dimension der Anlage (dim) und eine Rakete an einer bestimmten Stelle zurückgeben. Die Operation showAnlage soll die gesamte Anlage auf der Konsole ausgeben. Die set-Operation soll an den übergebenen Index die übergebene Rakete platzieren.

    Implementieren Sie die Klasse Feuerwerk wie oben beschrieben.

    Erstellen Sie eine Testklasse, in welcher Sie ein Objekt der Klasse Feuerwerk mit den Raketen so belgen, wie zu Beginn dieses Abschnittes dargestellt.
    Testen Sie die get-Operationen und showAnlage.
    Ersetzen Sie die blaue Rakete durch eine weiße Rakete.

    Eine weitere get-Operation soll ergänzt werden. Die Operation getRakete(String c) erhält eine Farbe als Zeichenkette übergeben und soll die erste Stelle zurückgeben, an dem sich eine Rakete der gesuchten Farbe befindet.
    Implementieren Sie die neue Operation getRakete.

    Die Operation hatFarbe soll überprüfen, ob eine übergebene Farbe in der Reihung anlage enthalten ist und in diesem Fall true zurückgeben, anderenfalls false.
    Implementieren Sie die Operation hatFarbe.

    Die Operation changeRakete(int i1, int i2, int i3, int i4) soll in der Reihung anlage die Raketen an den beiden übergebenen Positionen (i1,i2) und (i3,i4) tauschen.
    Implementieren Sie die Operation changeRakete.

    Nun soll es die Möglichkeit geben, die Flughöhe der Raketen der Reihung anlage zu speichern. Hierfür erhält die Klasse Feuerwerk eine zweites Attribut hoehe in Form einer zweidimensionalen Reihung vom Inhaltstyp Ganzzahl mit den Dimensionen der Reihung anlage.
    Verändern Sie den bisherigen Konstruktor so, dass er die Werte in hoehe auf 0 setzt.
    Implementieren Sie einen zweiten Konstruktor, dem zusätzlich zur Zeichenkettenreihung eine zweidimensionale Ganzzahlreihung übergeben wird, welche unter dem Attribut hoehe gespeichert werden soll.
    Erstellen Sie nun ein Objekt der Klasse Feuerwerk mit den Raketen wie im Einstieg des Abschnitts und zufälligen Flughöhen zwischen mindestens 50m und maximal 120m.

    Implementieren Sie eine Operation minHoehe, welche das Indexpaar des kleinsten Wertes der Flughöhe ermittelt und zurückgibt. Machen Sie dieses nochmal für maxHoehe.
    Implementieren Sie eine Operation ordneHöhe, welche den kleinsten Wert der Flughöhe an den Index (0,0) tauscht.

  1. Vergleichen Sie in einer eigenen Testklasse die beiden folgenden Algorithmen:
    int[] zahlen = {
        {1, 2, 3},
        {4, 5, 6},
        {7, 8, 9}
    };
    for (int i = 0; i < zahlen.length; i++) {
        for (int j = 0; j < zahlen[0].length; j++) {
            print(zahlen[i][j] + " ");
        }
        println();
    }
    
    
    int[] zahlen = {
        {1, 2, 3},
        {4, 5, 6},
        {7, 8, 9}
    };
    for (int[] zeile: zahlen) {
        for (int element : zeilen) {
            print(element + " ");
        }
        println();
    }
    
    
    Die linke Variante iteriert mit zwei geschachtelten for-Schleifen über die zweidimensionale Reihung zahlen.
    Die rechte Variante nutzt zwei geschachtelte for-each-Schleifen. Diese kann man alternativ zu for- Schleifen auch für zweidimensionale Arrays nutzen.
  1. Ein Objekt der Klasse Color ist eine Farbe in RGB-Codierung. Hierbei werden die Intensitäten der Grundfarben Rot, Grün und Blau in jeweils ganzzahligen Werten im Bereich von 0 bis 255 angegeben. Beispiele für konkrete Farben finden Sie unten.

    Farbe HTML-Name RGB-Dezimalcodierung
    Weiß (255,255,255)
    Schwarz (0,0,0)
    Rot (255,0,0)
    Limette (0,255,0)
    Blau (0,0,255)
    Gelb (255,255,0)
    Cyan (0,255,255)
    Magenta (255,0,255)
    Grün (0,128,0)
    Lila (128,0,128)
    Beispiele für die RGB-Codierung von Farben

    Die Klasse Feuerwerk wird um die Klasse Color und andere Funktionalitäten erweitert, siehe unten. Der Datentyp der Reihung anlage wird dadurch von Zeichenkette zu Color. In einer Challenge-Variante wird zusätzlich noch eine Klasse Rakete genutzt, wodurch der Datentyp der Reihung anlage von Zeichenkette zu Rakete wird.
    Entscheiden Sie sich zu Beginn dieser Aufgabe für eine der beiden Varianten. Die Klasse Color liegt bereits vor und kann entspechend genutzt werden.

  2. Klassenkarte der Klassen Feuerwerk und Color

    Verändern Sie Ihre bisherige Klasse Feuerwerk entsprechend der neuen Situation.

    Ist ein Platz der Reihung anlage nicht besetzt, wird eine Rakete mit der Farbe Schwarz mit Flughöhe 0 an die freie Stelle gesetzt.
    Verändern Sie die Konstruktoren entsprechend.
    Erstellen Sie ein neues Objekt der Klasse Feuerwerk und belegen Sie die Reihung anlage so, dass in der ersten Zeile rote Raketen, in der zweiten blaue, in der dritten alle Plätze frei, in der vierten grüne und in der fünften Zeile blaue Raketen platziert sind. Es soll insgesamt vier Spalten geben.

    Die Operation setRakete soll nun eine Rakete an einen bestimmten Platz setzen, wenn dieser Platz nicht besetzt ist.
    Verändern Sie die Operation setRakete nach diesen Vorgaben.
    Testen Sie die Operation, indem Sie eine weiße Rakete an die freie Stelle (schwarz) setzen.

    Die Operation zuenden der Klasse Feuerwerk erhält eine Reihung aus Farben als Übergabeparameter und soll zählen, wie viele Raketen der jeweiligen Farben in der Reihung anlage enthalten sind und deren Anzahlen in einer Ganzzahlreihung zurückgeben.
    Implementieren Sie die Operation zuenden.
    Testen Sie die Operation für rote und blaue Raketen.

    Klassenkarte der Klassen Feuerwerk, Rakete und Color

    Implementieren Sie die Klasse Rakete und nutzen Sie die Klasse Color entsprechend.

    Verändern Sie Ihre bisherige Klasse Feuerwerk entsprechend der neuen Situation.

    Ist ein Platz der Reihung anlage nicht besetzt, wird eine Rakete mit der Farbe Schwarz und 0.0 bzw. 0 für die anderen Attributswerte an die freie Stelle gesetzt.
    Verändern Sie den Konstruktor entsprechend.
    Erstellen Sie ein neues Objekt der Klasse Feuerwerk und belegen Sie die die Reihung anlage mit Raketen der Farben Rot, Blau, freier Platz, Grün, Blau, in der angegebenen Reihenfolge. Es oll insgesamt vier Spalten geben.
    Das Attribut laenge soll einen beliebigen Wert zwischen 10.0 und 25.0 haben, zdauer zwischen 1.0 und 3.0 und hoehe zwischen 20 und 60.

    Die Operation setRakete soll nun ein Objekt der Klasse Rakete an einen bestimmten Platz setzen, wenn dieser Platz nicht besetzt ist. Ist der Platz jedoch besetzt, soll die neue Rakete an den darauf folgenden Platz gesetzt und die restlichen Plätze nach hinten geschoben werden. Gegebenenfalls muss die letzte Rakete enfernt werden.
    Verändern Sie die Operation setRakete nach diesen Vorgaben.
    Testen Sie die Operation, indem Sie eine weiße Rakete an eine freie und eine besetzte Stelle setzen.

    Die Operation zuenden der Klasse Feuerwerk erhält eine Reihung aus Farben und eine Ganzzahl als Übergabeparameter. Sie soll zählen, wie viele Raketen der jeweiligen Farben in der Reihung anlage enthalten sind und gleichzeitig mindestens die übergebene Flughöhe erreichen und deren Anzahlen in einer Ganzzahlreihung zurückgeben.
    Implementieren Sie die Operation zuenden.
    Testen Sie die Operation für rote und blaue Raketen und einer Flughöhe von 40.

  1. (eA) Im vorherigen Abschnitt wurde die Klasse Magier verändert. Das neue UML-Klassendiagramm sieht nun wie folgt aus: Die vier Klassen werden Ihnen von Ihrer Lehrkraft in der Online-IDE freigegeben oder Sie verwenden Ihre eigenen.
    Der Magier hat auf einer Landkarte verzeichnet, wie magisch manche Orte sind. Ein geringer Wert spiegelt eine geringe Magie wieder und ein hoher Wert entspricht, dass der Ort sehr magisch ist. So sieht dann seine Übersicht am Ende, wie unten abgebildet aus.
    1 2 3 4 5 6 7 8 9
    A 2 7 4 6 7 2 1 1 1
    B 8 9 8 8 5 4 1 0 1
    C 2 8 7 1 1 1 1 1 1
    D 6 7 4 8 2 2 2 2 2
    E 6 4 7 2 2 1 1 5 5
    F 4 5 3 8 8 1 1 5 4
    G 1 1 2 9 7 2 3 4 7
  2. Implementieren Sie in der Klasse Magier das Attribut magischeOrte als zweidimensionale Reihung vom Inhaltstyp Ganzzahl und lassen Sie im Konstruktor die zweidimensionale Reihung mit zufälligen Ganzzahlwerten größer oder gleich 0 und kleiner oder gleich 9 initialisieren. Hinweis: Die Angabe A bis G und 1 bis 9 sind nur zur Orientierung und gehören nicht dazu.

    Implementieren Sie als nächste die Operation ausgabeMagischeOrte, mit welcher die Stärke der magischen Orte auf der Konsole angezeigt werden.

    Nun hat sich die magische Stärke mancher Orte geändert. So ist bspw. die Stärke bei B8 von 0 auf 2 gestiegen, dafür ist die Stärke bei B2 von 9 auf 7 gesunken.
    Implementieren Sie die Operation setMagischeOrte(int i1, int i2, int neuerWert), welche die Position der Änderung erhält (i1 ist die Zeile und i2 die Spalte) und anschließend den Wert an dieser Stelle ändert (neuerWert).

    Implementieren Sie die Operation getMagischeOrte(int i1, int i2), welche den Wert an der entsprechenden Position zurückgibt.

    Nun soll ermittelt werden, wie magisch diese abgebildete Region im Durchschnitt ist.
    Implementieren Sie die Operation durchschnittMagischeOrte, welche die durchschnittliche magische Stärke der Region ermittelt und anschließend zurückgibt.

    Als nächstes will der Magier wissen, wo der stärkste magische Ort in seiner Region ist.
    Implementieren Sie eine geeignete Operation maxMagischeOrte, welche die Indices des entsprechenden Ortes zurückgibt.
    Setzen Sie dieses ebenfalls für den Ort mit der geringsten magischen Stärke um.

    Die Reihung magischeOrte ist 7 Zeilen und 9 Spalten groß. Sie soll auf 10x10 vergrößert werden, die bisherigen Werte an den alten Stellen behalten und an allen neuen Stellen mit dem Wert 0 befüllt werden.
    Entwickeln Sie eine geeignete Lösungsstrategie für dieses Problem.