zoukankan      html  css  js  c++  java
  • poj 2421 Constructing Roads 解题报告

    题目链接:http://poj.org/problem?id=2421

            实际上又是考最小生成树的内容,也是用到kruskal算法。但稍稍有点不同的是,给出一些已连接的边,要在这些边存在的情况下,拓展出最小生成树来。

           一般来说,过到这四组数据大体上就能AC了。  1、题目给出的案例数据    2、连接的道路可能把所有的村庄都已经连通了       3、两个村庄给出多次,即连接这两个村庄的道路是重复的!。 

    2、3这两种情况的数据如下(为了好看,自己出了一组,当然Sample Input 那组也行):

    情况2(所有村庄已连通):                   情况3:

           还有第4种情况:

      1 #include <iostream>
      2 #include <algorithm>
      3 using namespace std;
      4 
      5 const int maxe = 10000 + 10;   // 这里开小点也行,因为只存储矩阵不够一半的数据
      6 int rep[maxe], vis[maxe];   
      7 
      8 struct sets
      9 {
     10     int v1, v2;
     11     int value;
     12 } exa[maxe];
     13 
     14 int cmp(sets a, sets b)
     15 {
     16     return a.value < b.value;
     17 }
     18 
     19 int find(int x)
     20 {
     21     return x == rep[x] ? x : find(rep[x]);
     22 }
     23 
     24 int main()
     25 {
     26     int i, j, n, a, b, x, y, t, cnt, flag;
     27     while (scanf("%d", &n) != EOF)
     28     {
     29         for (i = 1; i <= n; i++)
     30         {
     31             rep[i] = i;
     32         }
     33         cnt = 0;
     34         for (i = 1; i <= n; i++)
     35         {
     36             for (j = 1; j <= n; j++)
     37             {
     38                 scanf("%d", &a);
     39                 if (i < j)     // 只存储上三角矩阵
     40                 {
     41                     exa[cnt].v1 = i;
     42                     exa[cnt].v2 = j;
     43                     exa[cnt].value = a;
     44                     cnt++;
     45                 }
     46             }
     47         }
     48         sort(exa, exa+cnt, cmp);     // 对长度进行从小到大排序
     49         flag = 0;
     50         memset(vis, 0, sizeof(vis));
     51         scanf("%d", &t);
     52         while (t--)
     53         {
     54             scanf("%d%d", &a, &b);
     55             if (a > b)
     56                 swap(a, b);    // 刚开始就保持小的元素的祖先是大的元素
     57             x = find(a);    
     58             y = find(b);
     59             if (x > y)
     60             {
     61                 swap(x, y);     // 合并集合的时候,有可能使得大的元素的祖先变成了是比它小的元素
     62             }
     63             if (vis[a] && vis[b])   // 两个村庄在之前已经被访问过,这是为了处理情况4的情况的
     64                 rep[x] = y;
     65             else
     66             {
     67                 if (x == y)     // 所有村庄都有路可通
     68                     flag = 1;  
     69                 if (!vis[a] && !vis[b])
     70                 {    
     71                     rep[x] = y;
     72                     vis[a] = vis[b] = 1;
     73                 }
     74                 else if (!vis[a])
     75                 {
     76                     rep[x] = y;
     77                     vis[a] = 1;
     78                 }
     79                 else if (!vis[b])
     80                 {
     81                     rep[x] = y;
     82                     vis[b] = 1;
     83                 }
     84             }         
     85         }
     86         if (!flag)
     87         {
     88             int minval = 0;
     89             for (i = 0; i < cnt; i++)
     90             {
     91                 x = find(exa[i].v1);
     92                 y = find(exa[i].v2);
     93                 if (x != y)
     94                 {
     95                     minval += exa[i].value;
     96                     if (x < y)       // 为了与前面相一致,也是小的元素的祖先是大的元素
    97 rep[x] = y; 98 else 99 rep[y] = x; 100 } 101 } 102 printf("%d\n", minval); 103 } 104 else 105 printf("0\n"); 106 } 107 return 0; 108 }

           其实,还有一种比较简单的方法,但是目前还不会实现。Dwylkz给的解法:题目给的已连通的村庄的value都设为0。感觉这样会少讨论很多情况,希望以这种方法过了的读者可以指点一下,好像在上面的代码修改比较难实现。

  • 相关阅读:
    物联网操作系统HelloX开发者入门指南
    【 D3.js 高级系列 】 总结
    【 D3.js 高级系列 — 10.0 】 思维导图
    android fragment+ FragmentTabHost+viewpager 切换状态不保存的问题
    OpenGL 顶点缓存对象
    OpenGL顶点数组
    【 D3.js 高级系列 — 9.0 】 交互式提示框
    如何在 Linux 上录制你的终端操作
    程序员诗词大赛开始了_你看过吗?
    程序员与代码的搞笑日常
  • 原文地址:https://www.cnblogs.com/windysai/p/3313815.html
Copyright © 2011-2022 走看看