Python中使用Kruskal算法求最小生成树
Kruskal算法是一种求解最小生成树的贪心算法,主要步骤如下:
- 将所有边按照权值从小到大排序。
- 依次将每条边加入生成树中,如果加入该边后不会形成环,就将该边加入生成树中;否则将该边舍弃。
- 重复步骤2,直到生成树中包含了所有顶点。
下面是Python实现Kruskal算法的代码:
# 定义边 class Edge(object): def __init__(self, start, end, weight): self.start = start self.end = end self.weight = weight # 定义图 class Graph(object): def __init__(self, vertices): self.V = vertices self.edges = [] def add_edge(self, start, end, weight): self.edges.append(Edge(start, end, weight)) # 定义并查集 class UnionFind(object): def __init__(self, vertices): self.parent = {} for v in vertices: self.parent[v] = v def find(self, v): if self.parent[v] == v: return v self.parent[v] = self.find(self.parent[v]) return self.parent[v] def union(self, v1, v2): p1 = self.find(v1) p2 = self.find(v2) self.parent[p1] = p2 # Kruskal算法求最小生成树 def kruskal(g): uf = UnionFind(g.V) g.edges = sorted(g.edges, key=lambda e: e.weight) mst_weight = 0 mst_edges = [] for e in g.edges: start_root = uf.find(e.start) end_root = uf.find(e.end) if start_root == end_root: continue uf.union(e.start, e.end) mst_weight += e.weight mst_edges.append(e) return mst_weight, mst_edges # 示例 g = Graph(["p", "i", "d", "a", "n", "c", "o", "d", "e", "m"]) g.add_edge("p", "i", 1) g.add_edge("p", "d", 3) g.add_edge("i", "d", 2) g.add_edge("i", "a", 5) g.add_edge("d", "a", 4) g.add_edge("a", "n", 8) g.add_edge("a", "c", 7) g.add_edge("a", "m", 3) g.add_edge("n", "c", 6) g.add_edge("c", "o", 2) g.add_edge("c", "m", 9) print(kruskal(g))
上面的代码中,首先定义了边的类Edge和图的类Graph。然后定义了并查集类UnionFind,用于检查加入的边是否会形成环。最后定义了kruskal函数,实现Kruskal算法求解最小生成树。在示例中,我们给出了一个包含10个顶点的图,并求解了其最小生成树。
相关文章