poj 1797(并查集)

http://poj.org/problem?id=1797

题意:就是从第一个城市运货到第n个城市,最多可以一次运多少货。

输入的意思分别为从哪个城市到哪个城市,以及这条路最多可以运多少货物。

思路:我觉得可以用floyd来做这道题,结果交上去就TLE了,不过时间复杂度为n3TLE看起来也是比较正常,毕竟数字大。

然后我就看到网上有人用并查集来做,不然以前我都没往这方面想过,然后就用并查集来做

用并查集的思路就是,首先,对每组数据按照重量由大到小进行排序。然后查找合并。当Find(n) == Find( 1 )时,那个数据的重量也就是答案。

因为每组数据都是由大到小进行排序了,当前的重量肯定是最小的,而加入这一组数据后,上面的式子就成立了,也就说明这是第一次连通。

 1 #include <stdio.h>
 2 #include <string.h>
 3 #include <stdlib.h>
 4 
 5 struct cm{
 6     int x,y,weigh;
 7 }s[100005];
 8 
 9 int cmp(const void *a,const void *b)
10 {
11     return (*(cm *)b).weigh-(*(cm *)a).weigh;
12 }
13 
14 int belg[100005],m,n;
15 
16 int Find(int x)
17 {
18     int _x=x,_b;
19     while(belg[_x]!=_x)
20         _x=belg[_x];
21     while(x!=belg[x])
22     {
23         _b=belg[x];
24         belg[x]=_x;
25         x=_b;
26     }
27     return _x;
28 }
29 
30 int unio(int x)
31 {
32     belg[ Find( s[x].y ) ] = Find( s[x].x );
33     if( Find( 1 ) == Find ( n )) return 1;
34     return 0;
35 }
36 
37 int main()
38 {
39  //   freopen("in.txt","r",stdin);
40     int t,a=0,ans;
41     scanf("%d",&t);
42     while( t-- )
43     {
44         scanf("%d%d",&n,&m);
45         a++;
46         for( int i = 1 ; i <= n ; i++ )
47             belg[i]=i;
48         for( int i = 0 ; i < m ; i++ )
49             scanf("%d%d%d",&s[ i ].x,&s[ i ].y,&s[ i ].weigh);
50         qsort(s,m,sizeof(s[0]),cmp);
51         for( int i = 0 ; i < m ; i++ )
52             if(unio(i))
53             {
54                 ans = s[ i ].weigh;
55                 break;
56             }
57         printf("Scenario #%d:\n%d\n\n",a,ans);
58     }
59     return 0;
60 }

 

下面的是TLE了的Floyd(仅供参考,不敢确定正确性)

 1 #include <stdio.h>
 2 #include <string.h>
 3 
 4 int n,m,graph[ 1005 ][ 1005 ];
 5 
 6 int main()
 7 {
 8    // freopen("in.txt","r",stdin);
 9     int t,a = 0;
10     scanf("%d",&t);
11     while( t-- )
12     {
13         int b,c,d;
14         a++;
15         scanf("%d%d",&n,&m);
16         memset( graph , 1 , sizeof( graph ) );
17         for (int i = 1 ; i <= m ; i++ )
18         {
19             scanf("%d%d%d",&b,&c,&d);
20             graph[ b ][ c ] = d;
21          //   graph[ c ][ b ] = d;
22         }
23         for( int k = 1 ; k <= n ; k++ )
24             for( int i = 1 ; i < n ; i++ )
25                 for(int j = i+1 ; j <= n ; j++ )
26                     if( graph [ i ][ j ] > graph [ i ][ k ] && graph[ i ][ j ] > graph [ k ][ j ] )
27                         if( graph[ i ][ k ] > graph [ k ][ j ] )
28                             graph[ i ][ j ] = graph [ k ][ j ];
29                         else
30                             graph[ i ][ j ] = graph [ i ][ k ];
31         printf("Scenario #%d:\n%d\n\n",a,graph[ 1 ][ n ]);
32     }
33     return 0;
34 }

 

posted @ 2016-08-03 16:24  一个_小菜鸟  阅读(150)  评论(0编辑  收藏  举报