Informatik

Bäume und Graphen im Spiel

Im Kapitel Nichtlineare Datenstrukturen hast du Strukturen kennengelernt, die sich verzweigen. Spiele verzweigen sich überall: Ein Gegner entscheidet sich, ein Gespräch nimmt verschiedene Wendungen, eine Welt besteht aus Orten, die auf verschiedenen Wegen verbunden sind.

Die Leitfragen für dein Spiel:

  • Wo gibt es in deinem Spiel eine Folge von Fragen, an deren Ende eine Entscheidung steht? Das ist ein Baum.
  • Wo muss dein Spiel unter vielen Dingen schnell eins nach seinem Namen oder Wert finden? Das ist ein Suchbaum.
  • Wo ist etwas auf mehreren Wegen verbunden? Das ist ein Graph.

Woran es hakt

So sieht die Entscheidung eines Gegners aus, wenn man sie direkt hinschreibt:

if (this.distanceToSprite(ziel) < 160) {
   // verfolgen
} else {
   if (abstandZumPosten > 4) {
      // zurück zum Posten
   } else {
      // warten
   }
}

Das funktioniert. Aber wer einem zweiten Gegner ein anderes Verhalten geben will, kopiert die ganze Klasse und ändert die Verschachtelung. Dabei ist diese Verschachtelung bereits ein Baum, man sieht ihn nur nicht:

flowchart TD
    A{"Spieler nah?"} -->|ja| B["verfolgen"]
    A -->|nein| C{"weit vom Posten?"}
    C -->|ja| D["zurück zum Posten"]
    C -->|nein| E["warten"]

Mechaniken

Such dir mindestens eine aus. Du darfst sie verändern, kombinieren oder dir etwas ganz anderes ausdenken.

Ein Gegner, der sich entscheidet

Im Spiel: Eine Wache steht an ihrem Posten. Kommt der Spieler nah, verfolgt sie ihn. Ist er weg, kehrt sie zurück. Über ihrem Kopf steht, was sie gerade tut.

Dahinter steckt: ein Entscheidungsbaum als BinaryTree<String>. Innere Knoten tragen Fragen, Blätter tragen Handlungen. Links geht es bei ja weiter, rechts bei nein. Die Auswertung läuft von der Wurzel bis zu einem Blatt.

BinaryTree<String> verfolgen = new BinaryTree<String>("verfolgen");
BinaryTree<String> zurueck = new BinaryTree<String>("zurück zum Posten");
BinaryTree<String> warten = new BinaryTree<String>("warten");
BinaryTree<String> weg = new BinaryTree<String>("weit vom Posten?", zurueck, warten);
entscheidung = new BinaryTree<String>("Spieler nah?", verfolgen, weg);
private String entscheide() {
   BinaryTree<String> knoten = entscheidung;
   while (!knoten.getLeftTree().isEmpty()) {
      if (this.beantworte(knoten.getContent())) {
         knoten = knoten.getLeftTree();
      } else {
         knoten = knoten.getRightTree();
      }
   }
   return knoten.getContent();
}

Der Gewinn: Eine zweite Wache mit anderem Baum verhält sich anders, bei gleichem Programmcode.

Aufwand: ★★☆

Ein Gespräch mit Abzweigungen

Im Spiel: Eine Figur stellt Fragen. Je nach Antwort, J oder N, geht das Gespräch anders weiter und endet mit einem Geschenk, einem Auftrag oder einer Abfuhr.

Dahinter steckt: derselbe Aufbau wie beim Entscheidungsbaum. Nur beantwortet nicht das Programm die Fragen, sondern der Mensch an der Tastatur. Jeder Tastendruck geht einen Knoten tiefer.

Aufwand: ★★☆

Ein Monsterlexikon

Im Spiel: Ein Buch, in dem man jedes Monster nachschlagen kann, das man schon getroffen hat, alphabetisch sortiert.

Dahinter steckt: ein binärer Suchbaum. Ein Eintrag implementiert ComparableContent und vergleicht nach dem Namen. Die Ausgabe in alphabetischer Reihenfolge liefert ein Inorder-Durchlauf.

Aufwand: ★★★

Ein Fähigkeitenbaum

Im Spiel: Mit gesammelten Punkten schaltet man Fähigkeiten frei. Eine Fähigkeit geht erst, wenn die darüber schon freigeschaltet ist: erst „schneller laufen“, dann „rennen“ oder „springen“.

Dahinter steckt: ein Baum, in dem jeder Knoten eine Fähigkeit ist. Freischalten darf man nur Kinder von freigeschalteten Knoten.

Aufwand: ★★☆

Eine Weltkarte mit Wegen

Im Spiel: Mehrere Räume, durch Türen verbunden. Nicht jeder Raum ist mit jedem verbunden, und manche Wege sind länger.

Dahinter steckt: ein Graph mit den Abiturklassen Graph, Vertex und Edge. Räume sind Knoten, Türen sind Kanten, die Länge des Wegs ist das Gewicht. Jeder Raum kann eine eigene Bühne sein, wie bei Räume als eigene Bühnen in Objektorientierung im Spiel; der Graph sagt dann, welche Bühne hinter welcher Tür liegt. Ob jeder Raum erreichbar ist, beantwortet eine Tiefensuche, im Prinzip dieselbe wie die Flutfüllung aus dem Kapitel über Rekursion. Die Klassen findest du in der Referenz.

(Nur Leistungskurs.)

Aufwand: ★★★

Und ohne Spiel?

Im Spiel Derselbe Baum woanders
Gegner entscheidet sich ärztliche Diagnose, Kreditvergabe, Fehlersuche im Handbuch
Frage im inneren Knoten Merkmal in einem gelernten Entscheidungsbaum
Blatt trägt eine Handlung Klasse, in die eingeordnet wird
Baum tauschen, Auswertung behalten dasselbe Programm für andere Regeln

Entscheidungsbäume sind eines der ältesten Verfahren des maschinellen Lernens. Dort wird der Baum nicht von Hand gebaut, sondern aus Daten erzeugt. Die Auswertung bleibt genau die, die hier in zehn Zeilen steht.

Deine eigene Idee

Wo verzweigt sich etwas in deinem Spiel? Wo würdest du gern nach einem Namen nachschlagen? Was ist auf mehreren Wegen verbunden?

Fürs Tagebuch: Zeichne deinen Baum. Wie viele Fragen werden für eine Entscheidung höchstens gestellt? Wie ändert sich das, wenn du eine weitere Frage einfügst?

Checkpoint

Im Checkpoint nach diesem Kapitel steht oben rechts eine Wache. Sie entscheidet mit einem Entscheidungsbaum, ob sie den Spieler verfolgt, zu ihrem Posten zurückkehrt oder wartet, und sagt es. Wie du den Checkpoint lädst, steht auf der Startseite der Werkstatt.

Checkpoint: Bäume (Online-IDE)

Checkpoint: Bäume (Projekt für den Rechner)

Weiterbauen kannst du in deiner Werkstatt.

Bäume und Graphen im Spiel

Teilbare URL erstellen

Abschnitte auswählen