Minimum spanning tree algorithm
Topic
You are given an array of points representing points on a 2D plane, where points [i] = [xi, yi].
The cost of joining the points [xi, yi] and [xj, yj] is the Manhattan distance between them: | xi - xj | + | yi - yj |, where | val | represents the absolute value of val.
Please return the minimum total cost of connecting all points. All points are considered connected only when there is one and only one simple path between any two points.
Kruskel algorithm
Kruskal’s algorithm is an algorithm used to find the minimum spanning tree, but the implementation of the algorithm is different. It finds the minimum spanning tree by arranging the weights in descending order.
- Sort all edges in the original image from smallest to largest by weight.
Starting from the edge with the smallest weight, if the two nodes connected by this edge are not in the same connected edge in the graph, record the vertex as selected.
- Repeat step 2 until all nodes in the graph are connected, and the minimum spanning tree of the connected graph is found.
For the connection between nodes, belonging to the connectivity problem, you can use and lookup to achieve, the specific details can see my [previous blog] (https://sunra.top/posts/c2448c65/)
Based on the above ideas, we can derive the following algorithm:
And collect
1 | class UnionFind{ |
Algorithm body
1 | var minCostConnectPoints = function(points) { |
Rank merge
The above algorithm only adds path compression, but this path compression only reduces the depth of the connectivity tree maintained in our search set, not the depth of the tree we actually connect, so we introduce a new concept called rank.
The actual depth of each tree generated in the connection process is called rank. What we need to do is to try to connect the tree with a small rank to the root node of the tree with a large rank when merging. If the two trees to be merged are the same. If the rank of the tree is the same, pick one of them, insert the root node of another tree, and add one to the rank of the other tree, so that the rank of the last generated tree can be guaranteed to be the smallest.
So we revamped our union algorithm
1 | class UnionFind{ |
Prim algorithm
The steps of the Prim algorithm include:
Divide a graph into two parts, one part is classified as the point set U, and the other part is classified as the point set V. The initial set of U is {V1}, and the initial set of V is {ALL-V1}.
2. For U, start to find the one with the smallest weight of all associated edges of each node in U, then add the associated node Vi to U and delete it from V (note that a ring cannot be formed).
3. Recursion executes step 2 until the collection in V is empty.
4. The tree formed by all nodes in U is the minimum spanning tree.
Basic implementation of algorithm
1 | var minCostConnectPoints = function(points) { |
The above version is the most basic implementation of the algorithm, but there is still a lot of room for optimization.
Comparison
Method: Kruskal continuously searches for the smallest edge among all edges, and Prim searches for the connection with the smallest weight between the two sets of U and V. The common point is that the construction process cannot form a ring.
In terms of time: Prim is suitable for dense graphs with a complexity of O (n * n), so adjacency matrices are usually used for storage with a complexity of O (e * loge), while Kruskal is multi-purpose adjacency list, dense graph Prim > Kruskal, sparse graph Kruskal > Prim.
Spatially: Prim is suitable for less points and more sides, and Kruskal is suitable for more and less sides.