zoukankan      html  css  js  c++  java
  • Hlg 1748 【并查集】.cpp

    题意:

      n个数编号从1~n..但是并不按顺序排列..

      现在想把他们互换位置最后得到1~n的序列..

      两个数可以交换位置的条件是 |i-j| == bi

      

      输入:n 表示n个数

        a[1], a[2], a[3]..a[i]..a[n]

        b[1], b[2], b[3]..b[i]..b[n]

    思路:

      并查集..

      可以这么看..如果两个数在一个集合里,那么这两个数就可以互相交换位置了..

      所以就按照i+-b[i]把可以交换的位置的数和该数的归在一个集合里..

      最后查看是否所有要改的数都在一个集合里..

    Tips:

      加的时候加的应该是a[i], 表示把这些数放在一个集合里..

      最后看是不是要改位置的数正好都在一个集合里..

      如果把下标放在一个集合里就没有意义了..

    Code:

      

    View Code
     1 #include <stdio.h>
     2 #include <cstring>
     3 
     4 int f[110];
     5 int find(int x)
     6 {
     7     return f[x] == x?x:f[x] = find(f[x]);
     8 }
     9 
    10 int n;
    11 int a[110], b[110];
    12 
    13 int main()
    14 {
    15     freopen("in.txt", "r", stdin);
    16     bool flag;
    17     while (~scanf("%d", &n)) {
    18         flag = true;
    19         for (int i = 1; i <= n; ++i)
    20             f[i] = i;
    21         for (int i = 1; i <= n; ++i)
    22             scanf("%d", &a[i]);
    23         for (int i = 1; i <= n; ++i)
    24             scanf("%d", &b[i]);
    25         for (int i = 1; i <= n; ++i) {
    26             int ff = find(a[i]), fa, fb;
    27             if (i+b[i] < n) fa = find(a[i+b[i]]);
    28             if(i-b[i] > 0) fb = find(a[i-b[i]]);
    29             if (i+b[i] < n && fa != ff) {
    30                 f[fa] = ff;
    31             }
    32             if (i-b[i] > 0 && fb != ff) {
    33                 f[fb] = ff;
    34             }
    35         }
    36         for (int i = 1; i <= n; ++i) {
    37             if (find(i) != find(a[i])) {
    38                flag = false;
    39                break;
    40             }
    41         }
    42         if (flag) puts("YES");
    43         else puts("NO");
    44 
    45     }
    46     return 0;
    47 }

    链接:http://acm.hrbust.edu.cn/index.php?m=ProblemSet&a=showProblem&problem_id=1748

  • 相关阅读:
    一台服务器Nginx配置多个域名(一级域名或二级)
    Nginx启动和停止
    git删除本地及远程分支
    纯js实现复制内容到剪切板
    js 实现字符串转日期进行比较大小
    git 本地分支与远程分支 新建/删除/合并
    设置Git 记住密码
    炒鸡简单的javaScript的call和apply方法
    如何打war包
    Git 查看远程分支、本地分支、删除本地分支及远程分支
  • 原文地址:https://www.cnblogs.com/Griselda/p/3046358.html
Copyright © 2011-2022 走看看