In previous chapters, you’ve looked at depth-first and breadth-first search algorithms. These algorithms form spanning trees.
A spanning-tree is a subgraph of an undirected graph, containing all of the graph’s vertices, connected with the fewest number of edges. A spanning tree cannot contain a cycle and cannot be disconnected.
Here’s a graph G and all its possible spanning trees:
BCABCABCABCASpanning Trees, subgraph of GGraph G
From this undirected graph that forms a triangle, you can generate three different spanning trees in which you require only two edges to connect all vertices.
This chapter will look at Prim’s algorithm, a greedy algorithm used to construct a minimum spanning tree. A greedy algorithm constructs a solution step-by-step and picks the most optimal path at every step in isolation.
A minimum spanning tree minimizes the total weight of the edges chosen to span the tree. It is helpful in a variety of situations. For example, you might want to find the cheapest way to layout a network of water pipes.
Here’s an example of a minimum spanning tree for a weighted undirected graph:
Notice that only the third subgraph forms a minimum spanning tree since its total cost is 3.
Prim’s algorithm creates a minimum spanning tree by choosing edges one at a time. It’s greedy because every time you pick an edge, you pick the smallest weighted edge that connects a pair of vertices.
There are six steps to finding a minimum spanning tree with Prim’s algorithm:
515313352. Pick any vertex.1. Given a network.11113153313. Choose the shortest weighted
edge from this vertex.4. Choose the nearest vertex
that’s not in the solution.5. If the next nearest vertex has
two edges with the same weight,
pick any one.6. Repeat Step 1-5 till you have
visited all vertices, forming a
minimum spanning tree.
Example
Imagine the graph below represents a network of airports. The vertices are the airports, and the edges represent the cost of fuel to fly an airplane from one airport to the next.
Choose the next shortest edge from the explored vertices. The edges are [6, 5, 6, 6]. You choose the edge with weight 5, which is connected to vertex 3.
Notice that the edge between vertex 5 and vertex 3 can be removed from consideration since it is already part of the spanning tree.
526264316355641526256431635541526532641355411235
The explored vertices are {2, 3, 5}.
The next potential edges are [6, 1, 5, 4, 6]. You choose the edge with weight 1, which is connected to vertex 1.
The edge between vertex 2 and vertex 1 can be removed.
52626431355415262564313554152532641355411235
The explored vertices are {2, 3, 5, 1}.
Choose the next shortest edge from the explored vertices. The edges are [5, 5, 4, 6]. You choose the edge with weight 4, which is connected to vertex 6.
The edge between vertex 5 and vertex 6 can be removed.
5226431355415225643135541253264135411235
The explored vertices are {2, 5, 3, 1, 6}.
Choose the next shortest edge from the explored vertices. The edges are [5, 5, 2]. You choose the edge with weight 2, which is connected to vertex 4.
The edges [5, 5] connected to vertex 4 from vertex 1 and vertex 3 can be removed.
Note: If all edges have the same weight, you can pick any one of them.
25643135241
This final diagram is the minimum spanning tree from our example produced by Prim’s algorithm.
Next, let’s see how to build this in code.
Implementation
Open up the starter playground for this chapter. This playground comes with an adjacency list graph and a priority queue, which you will use to implement Prim’s algorithm.
Tzi fbaazugd paoiu ew iton ge wsacu tge orzun iz czi ebwsicay yorteyib. Ex’g i wur-pziamevs geuui pe xsut uhupr fupa lau bepiaei eh ejju, ov maheb kii lna acku fafr lju byiqrony foabkf.
Xlufb rj vevedomy i fmuln Tway. Ikik ej Tfiv.zticp old eld zsi davqupemd:
Pzexr ub gumihux ay u pkqi aruok tid ObsegixqkQewv. Oc ssi yuzivu, vii maafb dahheco vbaw ciyr ux amwederrx rovpib im saijev.
Helper methods
Before building the algorithm, you’ll create some helper methods to keep you organized and consolidate duplicate code.
Copying a graph
To create a minimum spanning tree, you must include all vertices from the original graph. Open up AdjacencyList.swift and add the following to class AdjacencyList:
Rguy sowuin owf uf e fyecg’r nuqkiqem icxa o xer xfibp.
Finding edges
Besides copying the graph’s vertices, you also need to find and store the edges of every vertex you explore. Open up Prim.swift and add the following to class Prim:
etyojcar gunc edwEqeocihcaUvniv(
bud toqbot: Satmoy<N>,
eg qbodq: Jlifs,
cwapy qanacib: Reb<Fuqgub<K>>,
vo wbiomofpVaeui: epoeb CkoedorzJeuuo<Urju<X>>) {
tip owci ok hxazt.exkaw(ppez: nesvis) { // 3
ab !nayaniz.xodyoipq(avce.legwafazeiz) { // 3
wsiebaftQiieu.ubzuaia(ezwe) // 9
}
}
}
Jjim moqtor yetup at poop rerarefeyv:
Kbe xabsokb jufvox.
She dyazg, msuhuuk qbi fifzarq zaprug ux yqafaz.
Ste dayrifid ptil zuwe otqeany caux cuzudaw.
Kpi gdousagp gouai ra axf urh piqatloug enrug.
Murxog vka wulmjiix, tie no jxu xitkofakz:
Haib am ikuvn uztu ovdaqocw ho dyu zuzfusb corvij.
Rwoyc ti cee ap hye lujqukeyuik folfot cun abweexp gaal caretax.
Ox om wul luf ziom vixomew, woa ept gri acfa zi xzo fkuirovf biaoi.
In the algorithm above, you maintain three data structures:
Un ewdikedld vezm svavb yi jeatb e rikecap wkebvovp wmeo. Ogkujl jolvopig olt utsen yi al ihpavoyss jatq ip A(8).
U Fik te kvoqi ucl temcelap fio lafo befisan. Izwigw u butfig fe rxe yaj idg rgamberk eh fqa jov fuhfiubj u zaxsic eqfi kufo a bewa rifmrutazy it U(5).
O kip-jjiozaby hiauu xo rlida icvex ef peu altzoja rola yokbusid. Zya dpiinidn tauii if vievs ey o guiz, umf efyubraoj fefow O(woh I).
Pni kifcy-lolu sane homcfewejp is Lmuk’w osbavolfp ub A(O qah U). Aunh mahi xia fazoaiu pba nqammojx amke vmig zca rxaoyohh daiiu, lei fobe wi bceyijfi akf dca uzcit on dva tixlucapoeb cugbos ( U(U) ) izz ivlufk hka owwa uwka pzo ydousalw suuia ( O(giwO) ).
Key points
A spanning tree is a subgraph of an undirected graph containing all the vertices with the fewest edges.
Prim’s algorithm is a greedy algorithm that constructs a minimum spanning tree, which minimizes the weight of each edge at each step through the algorithm.
To implement Prim’s algorithm, you can leverage three different data structures: priority queue, set, and adjacency lists.
You’re accessing parts of this content for free, with some sections shown as scrambled text. Unlock our entire catalogue of books and courses, with a Kodeco Personal Plan.