【JZOJ2017.08.14C组T3】羊羊修路(最小生成树)

题目描述

经过特色示范羊村检查,检查组觉得羊村的道路需要重修,破败的道路,会影响到小羊们上学的安全。

村长组织施工队,开始丈量距离,规划施工方案,已经得到了若干建筑物间修建道路的可行方案,共有N个建筑物,和M条可选道路。这些路保证可以将N个建筑相连。

最终方案中,羊村打算修建全球最豪华的全大理石道路,道路可以双向通行,且一体成型,路中无缝隙。为了达到这个设计要求,就必须自建大理石工厂!

大理石工厂建造的难度在于,必须根据其需要生产最大长度的大理石来设计。工厂可以生产出不超过其设计极限的任意长度的大理石。例如,设计长度为100的工厂,可以生产100、90等长度的大理石,但是不能生产长度为101的大理石。

羊村的预算有限,希望你能帮忙规划出一个修路方案,使得工厂的设计规模尽可能小,且可以保证其能生产的大理石可以连通所有羊村的建筑。求出工厂的最小设计规模。

输入

第一行两个整数N和M,N表示羊村中的建筑数量,M表示可以修建的道路数量。

接下来M行,每行三个整数Ai,Bi和Ci,表示从建筑Ai,到建筑Bi,可以修建一条长度为Ci的道路。

注意,建筑编号从1到N,两个建筑之间可能有多条道路。

输出

输出大理石工厂的最小设计规模

赤裸裸的最小生成树,只是将路径总和改成最长路径而已。

 1 #include <algorithm>
 2 #include <cstdio>
 3 
 4 struct edge{
 5     int from,to;
 6     long long dist;
 7 }e[10001];
 8 
 9 int n,m,pre[2001];
10 long long ans;
11 #define max(x,y) x>y?x:y
12 
13 bool cmp(edge x,edge y){
14     return x.dist<y.dist;
15 }
16 
17 int find(int x){
18     while(x!=pre[x])
19         x=pre[x];
20     return x;
21 }
22 
23 void join(int x,int y){
24     int fx=find(x);
25     int fy=find(y);
26     if(fx!=fy)pre[fx]=fy;
27 }
28 
29 int main(void){
30     scanf("%d%d",&n,&m);
31     for(int i=1;i<=n;++i)
32         pre[i]=i;
33     for(int i=1;i<=m;++i)
34         scanf("%d%d%lld",&e[i].from,&e[i].to,&e[i].dist);
35     std::sort(e+1,e+m+1,cmp);
36     for(int i=1;i<=m;++i){
37         if(find(e[i].from)!=find(e[i].to)){
38             ans=max(ans,e[i].dist);
39             join(e[i].from,e[i].to);
40         }
41     }
42     printf("%lld",ans);
43 }

 

posted @ 2018-07-26 15:37  gzh01  阅读(611)  评论(0编辑  收藏  举报