pku 2395

  1. #include <stdio.h>
  2. #include <string.h>
  3. #include <algorithm>
  4. typedef struct
  5. {
  6.     int u;
  7.     int v;
  8.     int w;
  9. }edge;
  10. typedef struct ufset
  11. {
  12.     int *parent;
  13. }ufset,*UFSet;
  14. UFSet Init(int N)
  15. {
  16.     UFSet U=new ufset[N+1];
  17.     U->parent=new int[N+1];
  18.     memset(U->parent,-1,sizeof(int)*(N+1));
  19.     return U;
  20. }
  21. int Find(UFSet U,int e)
  22. {
  23.     int eParent=e;
  24.     while(U->parent[eParent]>=0)
  25.         eParent=U->parent[eParent];
  26.     
  27.     int temp;
  28.     while(e!=eParent)
  29.     {
  30.         temp=U->parent[e];
  31.         U->parent[e]=eParent;
  32.         e=temp;
  33.     }
  34.     return eParent;
  35. }
  36. void Union(UFSet U,int p1,int p2)
  37. {
  38.     if(U->parent[p1]<U->parent[p2])
  39.     {
  40.         U->parent[p1]+=U->parent[p2];
  41.         U->parent[p2]=p1;
  42.     }
  43.     else
  44.     {
  45.         U->parent[p2]+=U->parent[p1];
  46.         U->parent[p1]=p2;
  47.     }
  48. }
  49. int cmp(const void *p1,const void *p2)
  50. {
  51.     return ((edge *)p1)->w - ((edge *)p2)->w;
  52. }
  53. void Kruskal(UFSet U,edge e[],int N,int M)
  54. {
  55.     int max=-1;
  56.     int i;
  57.     qsort(e+1,M,sizeof(edge),cmp);
  58.     for(i=1;i<=M;i++)
  59.     {
  60.         int p1=Find(U,e[i].u);
  61.         int p2=Find(U,e[i].v);
  62.         if(p1!=p2)
  63.         {
  64.             Union(U,p1,p2);
  65.             if(max<e[i].w)
  66.                 max=e[i].w;
  67.         }
  68.     }
  69.     printf("%d/n",max);
  70. }
  71. int main()
  72. {
  73.     int N,M;
  74.     int i;
  75.     while(scanf("%d%d",&N,&M)!=EOF)
  76.     {
  77.         UFSet U=Init(N);
  78.         edge *e=new edge[M+1];
  79.         for(i=1;i<=M;i++)
  80.             scanf("%d%d%d",&e[i].u,&e[i].v,&e[i].w);
  81.         Kruskal(U,e,N,M);
  82.         delete U->parent;
  83.         delete U;
  84.         delete e;
  85.     }
  86.     return 0;
  87. }
  88. /*
  89. WA了这么多次也该总结一下:
  90.    problem 1:  不会用c来编程,scanf(...!=EOF)是我总是出错的最大原因,哎,总是C++
  91.    编程,忽略了C里的一些用法和技巧
  92.    problem 2:  学会ACM方法 scanf() printf(),not cin cout ;
  93.                 学会一次直接分配数组(必要时或大多数时全局),而不要去用new delete 
  94.                 动态分配固然好,但速度慢;
  95. */
  96. /*
  97. 标准ACM:
  98. #include <stdio.h>
  99. #include <string.h>
  100. #include <algorithm>
  101. typedef struct
  102. {
  103.     int u;
  104.     int v;
  105.     int w;
  106. }edge;
  107. edge e[10005];
  108. int parent[2005];
  109. int Find(int e)
  110. {
  111.     int eP=e;
  112.     while(parent[eP]>=0)
  113.         eP=parent[eP];
  114.     
  115.     int temp;
  116.     while(e!=eP)
  117.     {
  118.         temp=parent[e];
  119.         parent[e]=eP;
  120.         e=temp;
  121.     }
  122.     return eP;
  123. }
  124. void Union(int p1,int p2)
  125. {
  126.     if(parent[p1]<parent[p2])
  127.     {
  128.         parent[p1]+=parent[p2];
  129.         parent[p2]=p1;
  130.     }
  131.     else
  132.     {
  133.         parent[p2]+=parent[p1];
  134.         parent[p1]=p2;
  135.     }
  136. }
  137. int cmp(const void *p1,const void *p2)
  138. {
  139.     return ((edge *)p1)->w - ((edge *)p2)->w;
  140. }
  141. void KruskalMinTree(int N,int M)
  142. {
  143.     int max=-1;
  144.     int i;
  145.     int j=0;
  146.     qsort(e+1,M,sizeof(edge),cmp);
  147.     for(i=1;i<=M;i++)
  148.     {
  149.         int p1=Find(e[i].u);
  150.         int p2=Find(e[i].v);
  151.         if(p1!=p2)
  152.         {
  153.             Union(p1,p2);
  154.             if(max<e[i].w)
  155.                 max=e[i].w;
  156.             j++;
  157.         }
  158.         if(j>=N-1)
  159.             break;
  160.     }
  161.     printf("%d/n",max);
  162. }
  163. int main()
  164. {
  165.     int N,M;
  166.     int i;
  167.     while(scanf("%d%d",&N,&M)!=EOF)
  168.     {
  169.         memset(parent,-1,sizeof(int)*(N+1));
  170.         for(i=1;i<=M;i++)
  171.             scanf("%d%d%d",&e[i].u,&e[i].v,&e[i].w);
  172.         KruskalMinTree(N,M);
  173.     }
  174.     return 0;
  175. }
  176. */
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值