//集合避圈法,以边为主导,从某一条边出发
#include<iostream>
using namespace std;
const int maxnum = 100;
typedef struct edge {
int u;
int v;
int w;
edge()
{
}
edge(int ui, int vi, int wi)
{
u = ui;
v = vi;
w = wi;
}
}edge;
int nodeset[maxnum];
int vexnums;
int edgenums;
edge e[maxnum];
int cmp(const void *a, const void *b)
{
edge* e1 = (edge*)a;
edge* e2 = (edge*)b;
return e1->w - e2->w;
}
//构建邻接矩阵
void CreateGraph() {
cout << "输入顶点数量和边数量:" << endl;
cin >> vexnums >> edgenums;
cout << "输入对应的边关系:" << endl;
for (int i = 0; i < edgenums; i++)
{
int u, v, w;
cin >> u >> v >> w;
e[i] = edge(u, v, w);
}
//对边集数组进行排序
qsort(e, edgenums, sizeof(e[0]), cmp);
for (int i = 1; i <= vexnums; i++)
{
nodeset[i] = i;
}
}
//合并顶点集合
int Merge(int u,int v) //默认情况下边u-v,u对应的是更新的顶点编号
{
int up = nodeset[u];
int vp = nodeset[v];
if (up == vp) return 0;
for (int i = 1; i <= vexnums; i++)
{
if (nodeset[i] == vp)
nodeset[i] = up;
}
return 1;
}
void Kruskal()
{
int ans = 0,n = vexnums;
for (int i = 0; i < edgenums; i++)
{
if (Merge(e[i].u, e[i].v))
{
ans += e[i].w;
n--;
cout << "n:" << n << " i:" << i<<endl;
if (n == 1)
{
cout << ans << endl;
return;
}
}
}
}
int main()
{
CreateGraph();
Kruskal();
return 0;
}
测试用例:
7 12
1 2 23
1 7 36
1 6 28
2 7 1
2 3 20
3 7 4
3 4 15
4 7 9
4 5 3
5 6 17
5 7 16
6 7 25
本文介绍了一种基于集合避圈法的最小生成树算法实现,通过使用C++编程语言,详细展示了如何构建邻接矩阵,对边集数组进行排序,并利用Kruskal算法求解最小生成树。该算法以边为主导,从某一条边出发,避免形成环路,最终得到权值最小的树。

2750

被折叠的 条评论
为什么被折叠?



