题目:
分析:
使用最小生成树算法解决,下面是分别使用了Kruskal算法和Prime算法:
代码:
Kruskal
#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
using namespace std;
const int MAXN = 1005;
int root[MAXN];
int n,m,ans,cnt;
struct node
{
int x,y;
int cost;
}no[MAXN*3];
bool Cmp(const node &n1,const node &n2)
{
return n1.cost < n2.cost;
}
int Getr(int x)
{
if(root[x] == x) return x;
else return root[x] = Getr(root[x]);
}
int main()
{
int st,ed,len;
scanf("%d%d",&n,&m);
for(int i=1;i<=n;++i)
root[i] = i;
for(int i=1;i<=m;++i)
{
scanf("%d%d%d",&st,&ed,&len);
no[i].x = st;
no[i].y = ed;
no[i].cost = len;
}
sort(no+1,no+m+1,Cmp);
for(int i=1;i<=m;++i)
{
int xx = Getr(no[i].x);
int yy = Getr(no[i].y);
if(xx != yy)
{
root[xx] = yy;
ans += no[i].cost;
}
}
for(int i=1;i<=n;++i)
if(root[i] == i)
cnt++;
if(cnt != 1)
printf("-1");
else
printf("%d\n",ans);
return 0;
}
Prime
#include <iostream>
#include <cstring>
#include <cstdio>
#define INF 0x3f3f3f3f
using namespace std;
const int MAXN = 1005;
int mat[MAXN][MAXN],dis[MAXN];
bool vis[MAXN];
int n,m,ans;
int main()
{
int st,ed,len;
memset(mat,INF,sizeof(mat));
memset(dis,INF,sizeof(dis));
scanf("%d%d",&n,&m);
for(int i=1;i<=m;++i)
{
scanf("%d%d%d",&st,&ed,&len);
mat[st][ed] = len;
mat[ed][st] = len;
}
dis[1] = 0;
int tmp,maxx;
for(int i=1;i<=n;++i)
{
tmp = -1,maxx = INF;
for(int j=1;j<=n;++j)
if(!vis[j]&&dis[j]<maxx)
{
maxx = dis[j];
tmp = j;
}
if(tmp == -1) break;
vis[tmp] = true;
ans += maxx;
for(int j=1;j<=n;++j)
if(!vis[j]&&mat[tmp][j]<INF&&mat[tmp][j]<dis[j])
dis[j] = mat[tmp][j];
}
if(tmp == -1)
printf("-1\n");
else
printf("%d\n",ans);
return 0;
}