雕刻时光

just do it……nothing impossible
  博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

最大边与最小边差最小的最小生成树——pku3522

Posted on 2011-02-20 09:29  huhuuu  阅读(391)  评论(0编辑  收藏  举报
我的思路是多次执行krusk,通过枚举比较产生最小min
ps:一般用g++提交要加上#include<stdio.h>(貌似废话了^ ^)
View Code
#include<iostream>
#include
<algorithm>
using namespace std;

#define MAX 0x3fffffff
int n,m;

struct data
{
int fr;
int to;
int w;
}edge[
10001];

int f[10001];
bool use[10001];

int cmp(data a,data b)
{
return a.w<b.w;
}

int find(int pos)
{
if(f[pos]==-1) return pos;
return f[pos]=find(f[pos]);//一定要加return
}

int un(int a,int b)
{
int fa=find(a),fb=find(b);
if(fa==fb)return 0;
f[fa]
=fb;return 1;
}

void krus()
{
int i,add=0,j,min,max,cha;
sort(
&edge[1],&edge[m+1],cmp);
cha
=MAX;
for(i=1;;i++)
{
for(j=1;j<=n;j++)//使每个顶点都为-1
f[j]=-1;

min
=MAX;max=0;
add
=0;
for(j=i;j<=m;j++)
{
if(un(edge[j].fr,edge[j].to)==1)
{
if(min>edge[j].w) min=edge[j].w;
if(max<edge[j].w) max=edge[j].w;
add
++;
}
}

int temp=max-min;
if(add==n-1)
{
if(temp<cha) cha=temp;
}
else
break;
}

if(cha==MAX)printf("-1\n");
else printf("%d\n",cha);
}

int main()
{
int a,b,i;
while(scanf("%d%d",&n,&m),n||m)
{
for(i=1;i<=m;i++)
{
scanf(
"%d%d%d",&edge[i].fr,&edge[i].to,&edge[i].w);
}
krus();
}
}