最小生成树(普里姆算法,克鲁斯卡尔算法)

#include<iostream>
#include<algorithm>
using namespace std;
typedef struct node{
	int start;
	int end;
	int pow;
}adjvex;
int vexnum,arcnum;
adjvex road[20];
int node[20];
bool cmp(adjvex &a,adjvex &b)
{
	return a.pow<b.pow;
}
int Find(int n)
{					//作用就是一个顶点顶点去寻找,知道找不下去为止(没有邻接点)
	if (node[n]==-1)   
		return n;
	return node[n]=Find(node[n]);
}
int Merge(int m,int n)
{
	int r1=Find(m);
	int r2=Find(n);
	if (r1==r2)		//说明有回路存在,不能把顶点加进去
		return 0;
	if (r1<r2)
		node[r2]=r1;
	else
		node[r1]=r2;
	return 1;
}
int main()
{
	memset(node,-1,sizeof(node));
	cout<<"请输入结点数与边数:\n";
	cin>>vexnum>>arcnum;
	int i;
	for (i=1;i<=arcnum;i++)
		cin>>road[i].start>>road[i].end>>road[i].pow;
	sort(road,road+arcnum+1,cmp);
	cout<<"------------------------\n";
	for (i=1;i<=arcnum;i++)
		cout<<road[i].start<<" "<<road[i].end<<" "<<road[i].pow<<endl;
	int count=0,sum=0;
	for (i=0;i<arcnum;i++)
	{
	   if (Merge(road[i].start,road[i].end))
	   {
	     count++;
		 sum+=road[i].pow;
	   }
	   if (count==vexnum-1)
		   break;
	}
	cout<<sum<<endl;
	return 0;
}

数据:9
14
1 2 4
1 8 8
2 3 8
2 8 11
3 4 7
3 6 4
3 9 2
4 5 9
4 6 14
5 6 10
6 7 2
7 8 1
7 9 6
8 9 7
//克鲁斯卡尔算法
#include<stdio.h>		//假设两点之间不连通时的距离为100,这个数可以根据现实情况改
#define maxsize 20
typedef struct node{
	int adj;
}Adjvex[maxsize][maxsize];
typedef struct{
	int vexnum,arcnum;
	int vex[maxsize];
	Adjvex arcs;
}Mgraph;
typedef struct{
	int adjvex;
	int lowest;
}closed;
int locate(Mgraph g,int u)
{
		int i;
		for (i=1;i<=g.vexnum;i++)
			if (g.vex[i]==u)
				return i;
			return 0;
}
void Creat(Mgraph &g)
{
	int i,j,start,end,s,e,pow;
	printf("请输入图的结点数与边数:\n");
	scanf("%d%d",&g.vexnum,&g.arcnum);
	printf("请输入顶点信息:\n");
	for (i=1;i<=g.vexnum;i++)
		scanf("%d",&g.vex[i]);
	for (i=1;i<=g.vexnum;i++)
		for (j=1;j<=g.vexnum;j++)
			g.arcs[i][j].adj=100;
		for (i=1;i<=g.arcnum;i++)
		{
		  printf("请输入边的起始端,终止端与权值:\n");
			scanf("%d%d%d",&start,&end,&pow);
		s=locate(g,start);
		e=locate(g,end);
		g.arcs[s][e].adj=g.arcs[e][s].adj=pow;
		}
		printf("输出矩阵为:\n");
		for (i=1;i<=g.vexnum;i++)
		{
			for (j=1;j<=g.vexnum;j++)
				printf("%d ",g.arcs[i][j].adj);
			printf("\n");
		}
}
void MinSpantree(Mgraph g,int u)
{
		int i,j,k,min;
		closed a[maxsize];
		k=locate(g,u);
		for (i=1;i<=g.vexnum;i++)
			if (i!=k)
			{
			    a[i].adjvex=u;
				a[i].lowest=g.arcs[k][i].adj;
			}
			a[k].lowest=0;
		for (i=2;i<=g.vexnum;i++)
		{
					min=100;
					for (j=1;j<=g.vexnum;j++)
						if (a[j].lowest&&a[j].lowest<min)
						{
						  min=a[j].lowest;
						 k=j;
						}
			printf("边:%d %d	权:%d\n",a[k].adjvex,g.vex[k],min);
		  a[k].lowest=0;
			for (j=1;j<=g.vexnum;j++)
			  if (a[j].lowest&&g.arcs[k][j].adj<a[j].lowest)
			  {
				a[j].lowest=g.arcs[k][j].adj;
				a[j].adjvex=g.vex[k];
			  }
		}
}
int main()
{
	Mgraph g;
	int u;
	Creat(g);
	printf("输入构建最小树的起点:\n");
    scanf("%d",&u);
	MinSpantree(g,u);
	return 0;
}
数据:
6 10
1 2 3 4 5 6
1 2 6
1 3 1
1 4 5
2 3 5
2 5 3
3 4 5
3 5 6
3 6 4
4 6 2
5 6 6
//普里姆算法


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值