Section07 Solutions
Section07 Solutions
1. Graph properties
(a) Consider the undirected, unweighted graph below.
F
D E A B
C
(i) V = {A, B, C, D, E, F, G} and E = {(D, G), (E, A), (A, B), (B, F ), (F, C), (C, B)}. This means that
|V | = 7 and |E| = 6.
(ii) The vertex with the max degree is B, which has a degree of 3.
(iii) There is indeed a cycle, between B, C, and F .
(iv) There are multiple simple paths with the maximum length: (E, A), (A, B), (B, F ), (F, C) or
(E, A), (A, B), (B, C), (C, F ) or their inverses (starting at C or F instead of E).
(v) We could add the edge (D, E).
(vi) One connected component is {D, G}. Another one is {E, A, B, C, F }.
1
(b) Consider the undirected, weighted graph below.
2 F
6 7
D E A B 3
8 C
5
(i) The path with the least number of nodes is (E, A), (A, B), (B, C). The cost is 21.
(ii) The minimum cost path is actually (E, A), (A, B), (B, F ), (F, C). The cost is 18.
(iii) The path with the shortest length is (E, A), (A, B), (B, C). The length is 3.
2. Graph traversal
(a) Consider the following graph. Suppose we want to traverse it, starting at node A.
B
E
G A
C
H F
D
If we traverse this using breadth-first search, what are two possible orderings of the nodes we visit? What if
we use depth-first search?
For the first ordering, you must run through adding/removing things from the queue/stack. To provide the
second ordering for each algorithm, you may simply look at the graph.
Solution:
2
(b) Same question, but on this graph:
B C
D E F G
Solution:
(b) Come up with pseudocode to implement depth-first search on a graph, given a starting node and an adjacency
list representation of the graph. Is your method recursive or not? What data structures do you use?
Solution:
3
4. Simulating Dijkstra’s
(a) Consider the following graph:
6
s t
5
8
7 4
2
9 7
y z x
Run Dijkstra’s algorithm on this graph starting from vertex s. What are the final costs of each vertex and the
shortest paths from s to each vertex? You can use the table below to keep track of each step in the algorithm.
Solution:
6
s: 0 t: 6
5
8
7 4
2
9 7
y: 7 z: 10 x: 10
The table below shows the final result of running Dijkstra’s algorithm.
4
(b) Here is another graph. What are the final costs and shortest paths if we run Dijkstra’s starting on node A?
2 2
3
7 1
A C D
12
4 2 1 2
E G F
7 2
Solution:
B: 2
2 2
3
7 1
A: 0 C: 7 D: 4
12
4 2 1 2
E: 9 G: 8 F: 6
7 2
2 4
3
7 1
A C D
8 5 10 6
E G F
9 0
(a) What happens if we run Kruskal’s algorithm? Give the set of edges in the resulting MST.
Solution:
We’ll use this table to keep track of components and edges we processed. The edges are listed in an order
sorted by weight.
5
Step Components Edge Include?
1 (F,G)
2 (C,D)
3 (A,B)
4 (B,C)
5 (B,D)
6 (C,E)
7 (D,F)
8 (A,C)
9 (A,E)
10 (E,G)
11 (D,G)
The resulting MST is a set of all edges marked as Include in the above table.
(b) Suppose we modify the graph above and add a heavier parallel edge between A and E, which would result in
the graph shown below. Would your answers for above be the same for this following graph as well?
2 4
3
7 1
A C D
11
8 5 10 6
E G F
9 0
Solution:
The steps are exactly the same, since we don’t consider the heavier edge when there are parallel edges.
The reason is that the heavier edge would never be considered as the best edge when there is a lighter one
(of weight 8) that can be added to the graph instead.
6
(a) A MST contains a cycle.
Solution:
(b) If we remove an edge from a MST, the resulting subgraph is still a MST.
Solution:
False, the set of edges we chose will no longer connect everything to everything else.
(d) If there are V vertices in a given graph, a MST of that graph contains |V | − 1 edges.
Solution:
7
(b) In this graph there are 6 vertices and 11 edges, and the for loop in the code for Kruskal’s runs 11 times, a few
more times after the MST is found. How would you optimize the pseudocode so the for loop terminates early,
as soon as a valid MST is found.
Solution:
Use a counter to keep track of the number of edges added. When the number of edges reaches |V | − 1,
exit the loop.
We can represent this as an undirected, unweighted graph where each tile is a vertex. Edges connect tiles we
can travel between. When we have a wormhole, we add an extra edge connecting that wormhole tile to the
corresponding end of the wormhole.
Because it takes only one turn to travel to each adjacent tile, there is actually no need to store edge weights: it
8
costs an equal amount to move to the next vertex.
All paths are bidirectional, so we can also use an undirected graph. (If there are paths or wormholes that are
one-way, we can switch to using a directed graph).
To find the shortest path, we can run BFS starting with the player and stop the moment we hit a coin.
(We can use other algorithms like DFS or Dijkstra’s algorithm if we’re careful, but those would be less efficient.)
Flavor Text You and your trusty Pikachu have made it halfway through Viridian Forest, but things have taken a
turn for the worst. That last Weedle poisoned your Pikachu, and you’re all out of antidotes.
In the Pokémon world, the poison doesn’t do any damage as long as you stay perfectly still. But every time you take
a step, the poison does a little bit of damage to your poor friend Pikachu.
Thanks to Bulbapedia1 , you know the exact map of Viridian Forest. Knowing that each step will cost your Pikachu
exactly one of its precious hit points, you will need to find an efficient path through the forest.2
Formal Statement In a video game you are playing, each step you take costs a character (Pikachu) one unit of
health. You have a map of the level (Viridian Forest) – your goal is to reach the end of the level (marked on your
map) while losing as little health as possible.
(a) Describe a graph and an algorithm run on that graph to find the path through the forest to save as many of
Pikachu’s hit points as possible (i.e. the path with the fewest number of steps).
Solution:
Have a vertex for each possible location in Viridian Forest, and an edge between every two vertices we can
move between in one step. Since Pikachu loses the same amount of hit points per step, we can just leave
the graph unweighted.
Since the graph is unweighted, we can just run BFS, starting from our current location, with a target of
the end of Viridian Forest.
You could use either a directed graph or an undirected graph for this part.
9
(b) Flavor Text You run your algorithm and come to a devastating realization – the edge of Viridian Forest
is at least 25 steps away, and Pikachu has only 20 hit points left. If you just walk to the end of the forest,
Pikachu will faint before reaching the next Pokémon Center. So you come up with a backup plan. Returning
to Bulbapedia, you see there is a potion just a little bit out of the way of the fastest path.
Brock tells you he knows how to update your graph to find the best path now. He says he’ll add a dummy
vertex to the graph where the potion is and connect up the new vertex with a (directed) edge of length −20,
to represent undoing the loss of 20 hit points.
Formal Statement You realize your character doesn’t have enough health to make it to the edge of the
forest. But you know there is a healing item (a “potion”) somewhere in the forest, that will give you back 20
units of health.
A friend (Brock) suggests the following update: add a dummy vertex to the graph where the healing item is
and connect up the new vertex with a (directed) edge of length −20, to represent undoing the loss of 20 hit
points.
9 spots in Viridian Forest, the corresponding vertices before Brock’s transformation and the same vertices
after the transformation.
Tell Brock why his representation isn’t quite going to work (hint: you can only use the potion once. What
happens if the potion edge is part of a cycle?).
Solution:
10
(c) You convince Brock to change the graph representation. You’ll now have two copies of the original Viridian
Forest graph, in copy 1 the potion is still unused. In copy 2, the potion is no longer there. You add an edge
of weight −20 from copy 1 to copy 2 at the location of the potion (crossing that edge represents using that
potion). His new graph looks something like this.
Brock says he’ll start running Dijkstra’s. Should you trust the output?
Solution:
No, Dijkstra’s isn’t guaranteed to work when there are negative edges. Poor Brock. He knows so much
about rock Pokemon but so little about algorithms.
Luckily your Pokédex gets good data service in Viridian Forest, and you look up the Bellman-Ford algorithm
for finding shortest paths with negative edge weights and find the new best path.
(d) Challenge Problem Misty says she knows about a second potion somewhere else in the forest. Describe
how to modify the graph to handle both of the potions.
Solution:
We now want 4 copies of the graph. One for each of (no potions used, only potion 1 used, only potion 2
used, both potions used). Make edges of weight −20 to connect these in the same way as you did in the
last part.
To make it easier to choose a final destination, add a dummy destination vertex. Then add a weight 0
edge from each copy of the edge of the forest to the dummy destination.
11