#include<iostream>
#include<string.h>
#define Max 50
using namespace std;
typedef struct student
{
int v1,v2;
int weight;
}edge;
typedef struct ss
{
edge a[Max];
int Vex; //顶点数量
int Arc; //边的数量
}*Graph,graph;
int get_parent(int v[],int p); //对于节点p求其父节点
void init_graph(Graph &L);
void creat_graph(Graph &L,int Vex);
void build_graph(Graph &L);
void insert_Edge(Graph &L,edge s);
void printlist(Graph L);
void sort_weight(Graph L); //按照权值的顺序从小到大排序
void Kruskal(Graph L,int &sum);
int main()
{
Graph L;
init_graph(L);
build_graph(L);
cout<<"您想创建几条边呢"<<endl;
int Arc;
cin>>Arc;
int i;
edge s;
for(i=0;i<Arc;i++)
{
cout<<"请输入第"<<i+1<<"条边的两个顶点以及其权值"<<0<<"---"<<L->Vex-1<<endl;
cin>>s.v1>>s.v2>>s.weight;
insert_Edge(L,s);
}
cout<<endl;
sort_weight(L);
cout<<endl;
int sum;
Kruskal(L,sum); //克鲁斯卡尔算法
cout<<"最小权值之和为"<<sum<<endl;
return 0;
}
void init_graph(Graph &L)
{
L=NULL;
}
void creat_graph(Graph &L,int Vex)
{
if(L!=NULL)
{
cout<<"此时已经有值了呦"<<endl;
return ;
}
else
{
L=new graph;
L->Vex=Vex;
L->Arc=0;
}
}
void build_graph(Graph &L)
{
cout<<"您想创建几个顶点呢"<<endl;
int Vex,Arc;
cin>>Vex;
creat_graph(L,Vex);
}
void insert_Edge(Graph &L,edge s)
{
if(L->Arc==Max)
{
cout<<"此时的边已经满了呦"<<endl;
return ;
}
L->a[L->Arc]=s;
L->Arc++;
}
void printlist(Graph L)
{
int i;
for(i=0;i<L->Arc;i++)
{
cout<<i<<" ("<<L->a[i].v1<<","<<L->a[i].v2<<") "<<L->a[i].weight<<endl;
}
}
void sort_weight(Graph L) //按照权值的顺序从小到大排序
{
int i,j;
for(i=0;i<L->Arc-1;i++)
{
for(j=0;j<L->Arc-i-1;j++)
{
if(L->a[j].weight>L->a[j+1].weight)
{
edge temp=L->a[j];
L->a[j]=L->a[j+1];
L->a[j+1]=temp;
}
}
}
}
int get_parent(int v[],int p) //对于节点p求其父节点
{
while(v[p]!=-1&&p>=0)
{
p=v[p];
}
return p; //返回其父节点
}
void Kruskal(Graph L,int &sum)
{
sum=0;
int t[L->Vex];//创建一个顶点数组大小的数组
memset(t,-1,sizeof(t));
sort_weight(L); //将权值有小到大排号好序列
int i,a,b;
for(i=0;i<L->Arc;i++) //枚举所有的边
{
a=get_parent(t,L->a[i].v1);
b=get_parent(t,L->a[i].v2);
if(a!=b)//不在痛一个连通块中
{
t[a]=b;//设置成在同一个连通块中
sum+=L->a[i].weight;
}
}
}
最小生成树最小权值(克鲁斯卡尔算法)
最新推荐文章于 2024-04-11 18:27:54 发布