编程语言
首页 > 编程语言> > 算法作业1.1-----用Prim算法构造最小生成树

算法作业1.1-----用Prim算法构造最小生成树

作者:互联网

Prim算法

普里姆算法(Prim算法),图论中的一种算法,可在加权连通图里搜索最小生成树。

算法描述

1).输入:一个加权连通图,其中顶点集合为V,边集合为E;
2).初始化:Vnew = {x},其中x为集合V中的任一节点(起始点),Enew = {},为空;
3).重复下列操作,直到Vnew = V:
a.在集合E中选取权值最小的边<u, v>,其中u为集合Vnew中的元素,而v不在Vnew集合当中,并且v∈V(如果存在有多条满足前述条件即具有相同权值的边,则可任意选取其中之一);
b.将v加入集合Vnew中,将<u, v>边加入集合Enew中;
4).输出:使用集合Vnew和Enew来描述所得到的最小生成树。

算法图解
在这里插入图片描述
以该图为例若选择A点作为起始点,则于A相邻的有三条边,又因为AB之间的权值最小,所以讲B加入Vnew。
在这里插入图片描述
此时A,B点都已经在Vnew集合中,所以五条邻接边,选择相邻权值最小的点加入Vnew集合。
在这里插入图片描述
重复以上操作直到所有的点都被选入Vnew,则得出最小生成树。
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
最后得到最小生成树
在这里插入图片描述

算法设计

算法分两个部分
1、初始化
2、查找最小权值边并更新路径

void prim(int graph[][MAX], int n)
{
	int Vnew[MAX];     //表示对应Dist的起点
	int Dist[MAX];     //储存已选点和未选点之间的相邻边
	int i, j, min, minid, sum = 0;
	for (i = 2; i <= n; ++i) { //对几个数组进行初始化,因为默认从下标1开始,所以i=2
		Vnew[i] = 1;
		Dist[i] = graph[1][i]; //将顶点1的邻接边读入
	}
	Vnew[1] = 0;
	
	for (i = 2; i <= n; i++) {//查找最小权值边并更新路径
		min = MAXCOST;
		minid = 0;
		for (j = 2; j <= n; j++) {
			if (min > Dist[j] && Dist[j] != 0) { //找出最小边和最小边对应的下标
				min = Dist[j];       
				minid = j;
			}
		}
		printf("%d--->%d : 权值为:%d\n", Vnew[minid], minid, min);
		sum += min;
		Dist[minid] = 0; //minid对应的最路路径为0
		for (j = 2; j <= n; j++)
		{
			if (graph[minid][j] < Dist[j])  //对这一点直达的顶点进行路径更新 //若
			{
				Dist[j] = graph[minid][j];
				Vnew[j] = minid; 
			}
		}
	}
	printf("最小权值和为:%d", sum);
}

源码

https://github.com/Lu-ziyan/-/blob/master/prim.cpp

Lu_ziyan 发布了0 篇原创文章 · 获赞 0 · 访问量 7 私信 关注

标签:Prim,1.1,最小,minid,Vnew,算法,权值,集合
来源: https://blog.csdn.net/IIIZONE/article/details/104516413