Algorithmen und Datenstrukturen (für ET/IT

Werbung
Programm heute
Algorithmen und Datenstrukturen (für ET/IT)
Wintersemester 2012/13
7 Fortgeschrittene Datenstrukturen
Dr. Tobias Lasser
Graphen
Bäume
Heaps
Computer Aided Medical Procedures
Technische Universität München
5
Traversierung von Binärbäumen
DFS Binärbaum
Sei G = (V , E ) Binärbaum.
Sei G = (V , E ) Binärbaum.
In welcher Reihenfolge durchläuft man G ?
Tiefensuche (Depth-first search, DFS) gibt es in 3 Varianten:
• Wurzel zuerst
1
• danach linker oder rechter Kind-Knoten l bzw. r ?
• besuche Wurzel
• durchlaufe linken Teilbaum
• durchlaufe rechten Teilbaum
• falls l: danach Kind-Knoten von l oder zuerst r ?
• falls r : danach Kind-Knoten von r oder zuerst l?
2
w
l
Pre-order Reihenfolge
w
In-order Reihenfolge
• durchlaufe linken Teilbaum
• besuche Wurzel
• durchlaufe rechten Teilbaum
r
linker Teilbaum
3
rechter Teilbaum
Post-order Reihenfolge
• durchlaufe linken Teilbaum
• durchlaufe rechten Teilbaum
• besuche Wurzel
→ falls zuerst in die Tiefe: Depth-first search (DFS)
→ falls zuerst in die Breite: Breadth-first search (BFS)
6
7
Pre-order Traversierung
In-order Traversierung
Pre-order Reihenfolge:
In-order Reihenfolge:
• besuche Wurzel
• durchlaufe linken Teilbaum
• durchlaufe linken Teilbaum
• besuche Wurzel
• durchlaufe rechten Teilbaum
• durchlaufe rechten Teilbaum
Beispiel:
Beispiel:
A
A, L, A, O, G, D, T, N, E
A
A, L, G, O, D, A, T, E, N
L
A
T
O
G
L
N
D
A
E
T
O
G
N
D
8
Post-order Traversierung
E
9
Beispiel: Arithmetischer Term
Post-order Reihenfolge:
+
• durchlaufe linken Teilbaum
• durchlaufe rechten Teilbaum
*
*
• besuche Wurzel
+
Beispiel:
3
A
A, G, D, O, L, E, N, T, A
L
A
2
3
4
Traversierung:
T
O
5
• Pre-order: + * + 3 4 5 * 2 3
N
• In-order: 3 + 4 * 5 + 2 * 3
G
D
E
• Post-order: 3 4 + 5 * 2 3 * +
10
11
Implementierung DFS Traversierung
Implementierung DFS Traversierung ohne Rekursion
Datenstruktur:
• Datenstruktur:
Knoten:
links
Wert
Knoten:
rechts
links
Wert
rechts
besucht
• Hilfsmittel: Stack von Knoten “knotenStack”
• Algorithmus preorder:
• Algorithmus postorder:
preorder(knoten):
if (knoten == NULL) return;
besuche(knoten);
preorder(knoten.links);
preorder(knoten.rechts);
postorder(knoten):
if (knoten == NULL) return;
postorder(knoten.links);
postorder(knoten.rechts);
besuche(knoten);
• Algorithmus inorder:
inorder(knoten):
if (knoten == NULL) return;
inorder(knoten.links);
besuche(knoten);
inorder(knoten.rechts);
• rekursive Algorithmen
• auf Call-Stack basiert
postorderIterativ(wurzelKnoten):
knotenStack.push(wurzelKnoten);
while ( !knotenStack.isEmpty() ) {
knoten = knotenStack.top();
if ( (knoten.links != NULL) && (!knoten.links.besucht) )
knotenStack.push(knoten.links);
else if ( (knoten.rechts != NULL) && (!knoten.rechts.besucht) )
knotenStack.push(knoten.rechts);
else {
besuche(knoten);
knoten.besucht = true;
knotenStack.pop();
}
}
12
Implementierung ohne Rekursion und ohne Stack
13
BFS Binärbaum
• Datenstruktur:
Sei G = (V , E ) Binärbaum.
vater
Knoten:
links
Wert
rechts
besucht
Breitensuche (Breadth-first search, BFS):
• besuche Wurzel
• für alle Ebenen von 1 bis Höhe
• besuche alle Knoten aktueller Ebene
postorderIterativeOhneStack(wurzelKnoten):
knoten = wurzelKnoten;
while (true) {
if ( (knoten.links != NULL) && (!knoten.links.besucht) )
knoten = knoten.links;
else if ( (knoten.rechts != NULL) && (!knoten.rechts.besucht) )
knoten = knoten.rechts;
else {
besuche(knoten);
knoten.besucht = true;
if (knoten.vater == NULL) break;
else knoten = knoten.vater;
}
}
Ebene 0
Ebene 1
Höhe = 3
Ebene 2
Ebene 3
14
15
Implementierung BFS Traversierung
Anwendung: Quadtree I
• Datenstruktur:
• 4-närer Baum heißt Quadtree
links
Knoten:
Wert
rechts
• Hilfsmittel: Queue von Knoten “knotenQueue”
Quadtree
breitensuche(wurzelKnoten):
knotenQueue = leer;
knotenQueue.enqueue(wurzelKnoten);
while ( !knotenQueue.isEmpty() ) {
knoten = knotenQueue.dequeue();
besuche(knoten);
if (knoten.links != NULL)
knotenQueue.enqueue(knoten.links);
if (knoten.rechts != NULL)
knotenQueue.enqueue(knoten.rechts);
}
Bild
0
1
1
2
3
5
6
7
8
5
7
9
10
11
9
10
11 12
4
8
12
16
Anwendung: Quadtree II
2
4
17
Programm heute
• Codierung des Baumes mit Binärziffern
Quadtree
Bild
0
7 Fortgeschrittene Datenstrukturen
1
1
1
2
3
4
0
0
1
0
5
6
7
8
0
1
0
0
5
7
9
10
11
12
0
0
0
0
Graphen
Bäume
Heaps
2
9
10
11 12
4
8
1001010000 0 00
18
19
Definition Heap
Bemerkungen zur Heap Definition
Definition Heap
Sei G = (V , E ) ein Binärbaum mit Wurzel w ∈ V . Jeder Knoten
v ∈ V sei mit einem Wert key (v ) verknüpft, die Werte seien durch
≤, ≥ geordnet.
G heißt Heap, falls er folgende zwei Eigenschaften erfüllt:
Sei G = (V , E ) Min-Heap.
• wir beschränken uns hier auf Min-Heaps, alle Aussagen gelten
• G ist fast vollständig, d.h. alle Ebenen sind vollständig gefüllt,
mit entsprechenden trivialen Änderungen auch für Max-Heaps
ausser auf der untersten Ebene, die von links her nur bis zu
einem bestimmten Punkt gefüllt sein muss.
• typische Keys von Knoten sind Zahlen, z.B. key : V → R
• weiteres Beispiel: Strings als Keys, lexikographisch geordnet
• G erfüllt die Min-Heap-Eigenschaft bzw. die
• ein Heap ist kein abstrakter Datentyp!
Max-Heap-Eigenschaft, d.h. für alle Knoten v ∈ V , v 6= w gilt
• Min-Heap: key (v .vater ) ≤ key (v )
• Max-Heap: key (v .vater ) ≥ key (v )
Entsprechend der Heap-Eigenschaft heißt G Min-Heap bzw.
Max-Heap.
21
20
Min-Heap: Beispiel
Heap Eigenschaften
Sei G = (V , E ) Heap mit Wurzel w ∈ V .
1
• G als Min-Heap bzw. Max-Heap hat immer Element mit
3
5
2
9
kleinstem bzw. größtem Key in Wurzel w
• G ist aber nicht vollständig sortiert (d.h. Traversierung liefert
8
nicht notwendigerweise vollständig sortierte Folge)
• Ist |V | = n, so hat G Höhe von Θ(log n)
• Keys sind hier natürliche Zahlen
• Baum ist fast vollständiger Binärbaum
• typische Operation: extrahiere kleinsten (bzw. größten) Key
(d.h. Wurzel), kurz: extractMin (bzw. extractMax)
• Baum erfüllt Min-Heap-Eigenschaft:
• für alle Knoten v (ausser Wurzel) gilt
• anschließendes Problem: Heap-Eigenschaft wiederherstellen,
als Operation: minHeapify (bzw. maxHeapify)
key (v .vater ) ≤ key (v )
22
23
Heap: extractMin
Heap: minHeapify
Sei G = (V , E ) Min-Heap mit Wurzel w ∈ V und |V | = n.
• Operation minHeapify auf Knoten v ∈ V zur
Sei G = (V , E ) Min-Heap mit Wurzel w ∈ V .
Wiederherstellung der Min-Heap-Eigenschaft
• Operation extractMin:
• entferne Wurzel w aus Heap G und liefere key (w ) zurück
• tausche letzten Knoten von G an Stelle von Wurzel
• stelle Heap-Eigenschaft wieder her mit minHeapify
Output: minimaler Key in G
extractMin(G ):
min = key (w );
w = letzter Knoten in G ;
minHeapify(G , w );
return min;
• Voraussetzung: nur Knoten v verletzt Min-Heap-Eigenschaft
• lasse v durch Heap absinken, bis Min-Heap-Eigenschaft
wiederhergestellt
Input: Knoten v
minHeapify(G , v ):
if (v ist Blatt) return;
knoten = Minimum von v .links und v .rechts;
if (key (knoten) < key (v ) ) {
tausche knoten und v ;
minHeapify(G , knoten);
}
1
3
5
2
9
8
• Komplexität: O(log n)
24
Beispiel extractMin / minHeapify
Heap erzeugen: buildMinHeap
1
Gegeben sei Knoten-Liste V mit |V | = n und Keys key (v ) für
v ∈ V.
• wie erzeugt man aus V einen Min-Heap G = (V , E )?
11
3
25
2
3
• erzeuge irgendwie fast vollständigen Binärbaum aus V
• wende minHeapify auf alle Knoten v ∈ V an
2
(nicht nötig für unterste Ebene des Baumes!)
5
9
8
5
9
8
extractMin
minHeapify
2
2
3
5
11
11
9
8
minHeapify
3
5
Input: Knoten-Liste V
Output: Min-Heap G
buildMinHeap(V ):
G = erzeuge beliebigen fast vollständigen Binärbaum aus V ;
for each Knoten v in G ausser unterster Ebene {
minHeapify(G , v );
}
8
9
11
• Komplexität: O(n)
(nicht nur O(n log n)!)
minHeapify
26
27
Beispiel buildMinHeap
5
5
1
3
8
9
2
1
11
3
2
9
5
2
9
11
1
1
3
8
8
3
11
5
2
9
8
11
http://xkcd.com/835/
28
Zusammenfassung
7 Fortgeschrittene Datenstrukturen
Graphen
Bäume
Heaps
30
29
Herunterladen