Graphentheorie Modulphase 08.03. – 10.07.2010, Kurse 05, 06, 07 - Menge von Ecken und Kanten Ecke - Jede Kante verbindet zwei Ecken. - Der Grad einer Ecke gibt an, wie viele Kanten von einer Ecke ausgehen. Kante - Eine Schleife erhöht den Grad um zwei. Isolierte Ecke 2 3 2 3 4 Schleife Anfangs lernten wir Graphen kennen, bewiesen einfache Eigenschaften von Graphen (z.B. ist ein Graph eulerisch, wenn der Grad aller Ecken gerade ist), und beschäftigten uns mit einfacheren Aufgaben, wie das Prüfen zweier Graphen auf Isomorphie (bedeutet Gleichheit). - Unbewerteter Graph: alle Kantenwerte gleich - Bewerteter Graph: festgelegte Kantenlängen (Gewichte) Graphen im Alltag - Adjazenzmatrix: Tabelle, in der man sieht, welche Ecken miteinander verbunden sind. Hat man den Verdacht, dass zwei Graphen isomorph (gleich) sind, kann man dies mithilfe der Adjazenzmatrix herausfinden. Adiazenzmatrix des Graphen Wir sehen in unserer Umgebung übrigens auch jeden Tag Graphen: jedes Straßenbahnnetz ist ein Graph, ebenso wie verlegte Kabel. Dabei ist jeder Stecker oder jedes Gerät eine Ecke und jedes Kabel eine zwei Ecken verbindende Kante. Vom Problem zum Algorithmus Spezielle Graphen: Hamiltonscher Graph: hamiltonisch Nicht hamiltonisch Eulertour: Eine Eulertour ist ein Weg, der jede Kante des Graphen genau einmal enthält und bei dem Anfangs- und Endpunkt übereinstimmen. Tree: Ein Baum ist ein Graph, dessen Ecken mit möglichst wenig Kanten verbunden sind und in dem es keine Kreise gibt. Minimal Spanning Tree: Der Minimal Spanning Tree ist ein spezieller Tree in bewerteten Graphen. In ihm sind alle Ecken mit möglichst wenigen Kanten verbunden, die mit einem möglichst kleinen Gesamtgewicht bewertet sind. Die Breitensuche bestimmt die Länge des kürzesten Wegs zwischen zwei Ecken in einem unbewerten Graph. Einführung 0 Ein geschlossener Weg, der jede Ecke genau einmal enthält, heißt hamiltonscher Kreis, der nur in Hamiltonschen Graphen möglich ist. Ein Breitensuchprogramm Was haben wir gemacht? Was ist ein Graph? Für das Poster verantwortlich: Julia Klein, Janek Wettstein, Mirjam Schäfer, Sebastian Baur, Silvie Müller Wir behandelten verschiedene Problemstellungen, z.B. den kürzesten Weg von einer U-Bahn-Station zu einer anderen zu finden. Für dessen Bestimmung gab es verschiedene Lösungsansätze. Zuerst setzten wir das Netz in einen Graphen um und versuchten Strategien für das Finden von kürzesten Wegen zu bestimmen, was zu in Worten gefassten Algorithmen führte. Um intensiv daran arbeiten zu können verbrachten wir ein Wochenende im Landschulheim in Unterhöllgrund. Dabei kam auch der Spaß nicht zu kurz. Computeralgorithmen Unser eigentliches Ziel war allerdings, Algorithmen für einen Computer zu programmieren. Dies wurde mit Hilfe von „Cinderella“, einem dynamischen Geometrieprogramm, während zwei Treffen mit dessen Entwicklern Prof. Kortenkamp und Dr. Fest an der PH Karlsruhe umgesetzt. Dabei wurden neben einfachen Algorithmen, wie z.B. der Tiefensuche, auch kompliziertere programmiert, beispielsweise ein Algorithmus zum Bestimmen eines Minimal-Spanning-Trees. private Graph graph; private VertexQueue queue = new VertexQueue(); private Hashtable<Vertex, Vertex> vorgaenger; @Override protected void init() { this.graph = this.getGraph(); } @Override protected void runAlgorithm() { Vertex startVertex = this.getStartVertex(this.graph); Vertex endVertex = this.getFinishVertex(this.graph); this.queue = new VertexQueue(); this.queue.add(startVertex); this.vorgaenger = new Hashtable<Vertex,Vertex>(); boolean endpunktGefunden = false; while (!queue.isEmpty() || endpunktGefunden) { Vertex v = queue.remove(); Iterator<Edge> kantenIterator = this.graph.outgoing(v).iterator(); while (kantenIterator.hasNext()) { Edge e = kantenIterator.next(); Vertex x = e.otherVertex(v); if (!this.vorgaenger.containsKey(x)) { this.vorgaenger.put(x, v); this.queue.add(x); if (x.equals(endVertex)) { endpunktGefunden = true; break; } } } } Vertex v = endVertex; while (!v.equals(startVertex)) { Vertex parent = this.vorgaenger.get(v); this.graph.findEdge(parent, v). setColor(Color.BLUE); v = parent; } } Initialisiere den Graphen Bestimme den Start- und Endpunkt Lege eine Queue an und füge den Startpunkt hinzu, erstelle eine Hashtable (weist einem Schlüsselwert einen anderen Wert zu) Wiederhole, solange der Endpunkt nicht gefunden wurde oder die Queue leer ist. Nimm den ersten Punkt aus der Queue. Iteriere durch alle ausgehenden Kanten und bestimme anderen Knoten (der nicht v ist). Prüfe, ob für diesen Knoten schon ein Vorgänger eingetragen ist (d.h. ob er schon geprüft wurde), falls nicht, Knoten v als Vorgänger von Knoten x festlegen und Knoten x zur Queue hinzufügen Prüfe, ob Knoten x der Endpunkt ist Verfolge Weg zurück, indem man sich vom Endpunkt aus die Vorgänger bestimmen lässt, bis man beim Startpunkt landet.