您的位置:首页 > 产品设计 > UI/UE

并查集+贪心 Conquer a New Region HDU 4118 && ZOJ 3659

2014-08-14 16:27 274 查看
据说是区域赛的题,拿到的时候可把我吓坏了,没想到是水水的一题

题意:

输入N表示N个城市,再输入N-1条路a,b,c,c是这条路的运载能力

计算以一个一个城市开始到各个城市运输的最大量

输入

5

1 2 1

2 3 1

2 4 1

4 5 1

则以2或4为中心,输出1+1+2+1=5

输入

5

1 2 1

2 3 1

2 4 1

4 5 1

则以4为中心,输出1+1+2=4

#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#define maxn 200005
using namespace std;
struct xxx
{
int u,v,w;
}num[maxn];            //存下输入的路,方便排序
int f[maxn];           //父节点
int level[maxn];       //当前点内包含点的个数
long long sum[maxn];   //当前点的运输量的和
int find(int i)        //找根节点
{
if(i==f[i])
return f[i];
f[i]=find(f[i]);
return f[i];
}
int cmp(xxx a,xxx b)
{
return a.w>b.w;
}
int main()
{
int n;
int i,j;
while(scanf("%d",&n)!=EOF)
{
for(int i=0;i<n-1;i++)
scanf("%d%d%d",&num[i].u,&num[i].v,&num[i].w);
sort(num,num+n-1,cmp);             //先排序,再处理
for(int i=1;i<=n;i++)              //初始化
{
sum[i]=0;
f[i]=i;
level[i]=1;
}
long long ans=0;
i=0;
for(i=0;i<n;i++)
{
int fr,ed;
fr=find(num[i].u);
ed=find(num[i].v);
if(fr!=ed)
{
long long t1,t2;                               //注意开long long,没开WA了一发
t1=sum[fr]+(long long )num[i].w*level[ed];    //比较两种方式较大的一种,选择合适的中心
t2=sum[ed]+(long long )num[i].w*level[fr];
if(t1>t2)
{
f[ed]=fr;
level[fr]+=level[ed];
sum[fr]=t1;
ans=t1;
}
else
{
f[fr]=ed;
level[ed]+=level[fr];
sum[ed]=t2;
ans=t2;
}
}
}
printf("%lld\n",ans);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: