prim算法---最小生成树

来源:互联网 发布:tcp端口重复使用 编辑:程序博客网 时间:2024/06/05 19:02
Prim算法用于求无向图的最小生成树
设图G =(V,E),其生成树的顶点集合为U。
①、把v0放入U。
②、在所有u∈U,v∈V-U的边(u,v)∈E中找一条最小权值的边,加入生成树。
③、把②找到的边的v加入U集合。如果U集合已有n个元素,则结束,否则继续执行②。
其算法的时间复杂度为O(n^2) Prim算法实现:


根据步骤中的指示,我们在编写prim函数时,注意两点:

1、将与当前结点pos连接,并且最小权值的点加入进来,并且代替pos,进行第2步;

2、更新权值lowcost [ ] ,因为加入了新的结点,应当重新去计算lowcost [ ] 的各个值。


代码如下:

#include <stdio.h>#include <string.h>#include <stdlib.h>#include <time.h>#define MaxInt  0x3f3f3f3f#define N    100int map[N][N],low[N],visited[N];int n;int prim(int pos){ int i,j,min,result = 0; memset(visited,0,sizeof(visited)); //从某点开始记录和标记该点 visited[pos] =1;  //第一次给low数组赋值     for( i =0; i < n; i++)   if(i!= pos) low[i] = map[pos][i]; for(i =0; i < n-1; i++) {min = MaxInt;for(j = 0 ; j < n; j++)if(visited[j]==0 && min > low[j]){//找出与点pos相连的权值最小的点加入已访问结点的阵营min = low[j];pos = j;}result += min;printf("%d\n",min);visited[pos] =1;//访问过该点for(j = 0; j < n; j++){//加入pos点之后更新权值low[]if(visited[j] == 0 && low[j] > map[pos][j]){low[j] = map[pos][j];}}  }return result;}int main(){   int i,j,ans;   scanf("%d",&n);   memset(map,MaxInt,sizeof(map));   srand((unsigned int)time(NULL));   for(i=0; i < n; i++)   for(j = i+1; j < n ;j ++)   map[i][j] = map[j][i] = rand()%10000;   ans = prim(0);   printf("\n ans = %d\n",ans);return 0;}


参考博客:

http://www.cnblogs.com/Veegin/archive/2011/04/29/2032388.html



原创粉丝点击