zoukankan      html  css  js  c++  java
  • 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:
    %d
    
    ",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:
    %d
    
    ",a,graph[ 1 ][ n ]);
    32     }
    33     return 0;
    34 }
  • 相关阅读:
    关于使用JavaMail注册激活邮箱的注意点
    Maven Web报错:org.apache.jasper.JasperException: Unable to compile class for JSP
    IDEA的中文乱码问题
    深入了解Java动态代理与反射机制
    String、StringBuffer和StringBuilder的区别
    Java中HashCode()和equals()的关系
    Java中向下转型的意义
    局部内部类访问局部变量的问题
    Java内部类的应用场景
    Python os.rmdir() 方法
  • 原文地址:https://www.cnblogs.com/Tree-dream/p/5733406.html
Copyright © 2011-2022 走看看