一、Prim算法构造最小生成树
问题:举一个实例,画出采用Prim算法构造最小生成树的过程
二、分析:
1、首先选定顶点1加入最小生成树集合
2、以顶点1作为最小生成树集合,寻找到其余顶点构成的未选集合中权值最小的一条边,此处寻找到顶点2,并将顶点2加入集合。
3、以顶点2、3作为最小生成树集合,寻找至其余顶点构成集合权值最小的边,此处找到顶点6
……
6、以此类推,加入最后一个顶点4,最小生成树集合包含了所有顶点,找到了该算法下的一种最小生成树(最小生成树不唯一)
三、核心函数代码
void prim() {
int temp = 111, c = 1;
vis[1] = 1;//从顶点1开始创建最小生成树集合
printf("%d ", 1);//打印顶点1
for (int i = 2; i <= n; i++) {
dis[i] = a[1][i];
if (dis[i] < temp) {
temp = dis[i];
p = i;
}
}//寻找顶点1至其余未选顶点集合权值最小的边,顶点值返回到p
vis[p] = 1;
dis[p] = 111;
c++;//标记已加入生成树集合的顶点个数
printf("%d ", p);//输出找到的顶点p
while (c < n) {//循环找到所有顶点
temp = 111;
for (int i = 2; i <= n; i++) {
//更新可通路顶点集合
if (dis[i] > a[p][i] && vis[i] == 0) {
dis[i] = a[p][i];
}
}
//寻找可通路顶点集合中的最小值,找到下一个生成树顶点
for (int j = 2; j <= n; j++) {
if (dis[j] < temp) {
temp = dis[j];
p = j;
}
}
vis[p] = 1;//标记访问
dis[p] = 111;//对应p顶点在可通路集合中的值放大,不参与筛选计算
c++;
printf("%d ", p);
}
}
四、源码
https://github.com/sbjv/wuwuwu