zoukankan      html  css  js  c++  java
  • Separate the Animals

    There are some animals in a zoo which can be described as a grid with N rows and M columns. Your task is to place some obstacles so that no pairs of animals can reach each other.

    Two animals can reach each other if and only if their cells are 4-connected. For example, in Figure 1, the central blue cell can be reached by the four red cells, and cannot be reached by the other four white cells.

    sep1.JPG

    Figure 1

    What is more, you must put obstacles in exactly K cells, which are 4-connected and form exactly H holes. Here a hole is defined as a 4-connected part with finitely many open cells while the zoo is placed in an infinite open grid. For example, there are 2 holes (the green and the yellow areas) in Figure 2.

    sep2.JPG

    Figure 2

    For the following grid with two animals:

    sep3.jpg

    Figure 3

    If K = 8 and H = 1, one way to separate them is the following:

    sep4.jpg

    Figure 4

    Figure 5 is illegal because it contains no hole.

    sep5.jpg

    Figure 5

    Figure 6 is also illegal because the obstacles are not 4-connected.

    sep6.jpg

    Figure 6

    Given some animals, you are supposed to count the number of different solutions.

    Input Specification:

    Each input file contains one test case. For each case, the first line gives four integers: N, M, K, H (2 ≤ N, M ≤ 6; 1 ≤ K ≤ 12; 0 ≤ H ≤ 2). All the numbers are separated by spaces.

    Then N lines follow, each contains M characters, which are either . or O, representing an open cell or an animal, respectively. There will be at least 2 animals.

    Output Specification:

    For each case, print a single line containing a single integer: the number of solutions.

    Sample Input:

    3 5 8 1
    ...O.
    .O...
    .....
    
     

    Sample Output:

    8
      1 #include<map> 
      2 #include<set>
      3 #include<ctime>  
      4 #include<cmath>      
      5 #include<queue>   
      6 #include<string>  
      7 #include<vector>  
      8 #include<cstdio>      
      9 #include<cstring>    
     10 #include<iostream>  
     11 #include<algorithm>      
     12 #include<functional>  
     13 using namespace std;
     14 #define ms(x,y) memset(x,y,sizeof(x))      
     15 #define rep(i,j,k) for(int i=j;i<=k;i++)      
     16 #define per(i,j,k) for(int i=j;i>=k;i--)      
     17 #define loop(i,j,k) for (int i=j;i!=-1;i=k[i])      
     18 #define inone(x) scanf("%d",&x)      
     19 #define intwo(x,y) scanf("%d%d",&x,&y)      
     20 #define inthr(x,y,z) scanf("%d%d%d",&x,&y,&z)    
     21 #define infou(x,y,z,p) scanf("%d%d%d%d",&x,&y,&z,&p)   
     22 #define lson x<<1,l,mid  
     23 #define rson x<<1|1,mid+1,r  
     24 #define mp(i,j) make_pair(i,j)  
     25 #define ff first  
     26 #define ss second  
     27 typedef int LL;
     28 typedef pair<LL, LL> pii;
     29 const int low(int x) { return x&-x; }
     30 const double eps = 1e-6;
     31 const int INF = 0x7FFFFFFF;
     32 const int mod = 1e9 + 7;
     33 const int N = 15;
     34 int n, m, t, h;
     35 int fa[N*N][N*N], ga[N*N][N*N], sa[N*N][N*N], a[N][N], ans, vis[N][N];
     36 int ha[N*N][N*N], hole[N], b[N*N];
     37 char s[N][N];
     38 int dir[4][2] = { 0,1,0,-1,1,0,-1,0 };
     39  
     40 int get(int fa[], int x) {
     41   return fa[x] == x ? x : fa[x] = get(fa, fa[x]);
     42 }
     43  
     44 void dfs(int now, int cnt, int con) {
     45   if (cnt > t) return;
     46   if (con - 1 > t - cnt) return;
     47   if (t - cnt > n*m - now + 1) return;
     48   if (now > n * m) {
     49     if (cnt < t || con != 1 || hole[now - 1] != h) return;
     50     ans++; 
     51     return;
     52   }
     53  
     54   int x = (now - 1) / m + 1, y = (now - 1) % m + 1;
     55   rep(i, 1, n*m) {
     56     fa[now][i] = fa[now - 1][i];
     57     ga[now][i] = ga[now - 1][i];
     58     sa[now][i] = sa[now - 1][i];
     59     ha[now][i] = ha[now - 1][i];
     60   }
     61   hole[now] = hole[now - 1] + 1;
     62   if (con == 1 && cnt == t) {
     63  
     64   }
     65   else if (now > m) {
     66     int sz = 0;
     67     rep(i, 1, m) {
     68       int x = (now - i - 1) / m + 1, y = (now - i - 1) % m + 1;
     69       if (!a[x][y]) continue;
     70       b[sz++] = get(fa[now], now - i);
     71     }
     72     sort(b, b + sz);
     73     sz = unique(b, b + sz) - b;
     74     if (sz < con) {
     75       return;
     76     }
     77   }
     78  
     79   if (y > 1 && !a[x][y - 1]) {
     80     int fx = get(ha[now], now), fy = get(ha[now], now - 1);
     81     if (fx != fy) {
     82       if (!fx || !fy) ha[now][fx + fy] = 0;
     83       else  ha[now][fx] = fy;
     84       hole[now]--;
     85     }
     86   }
     87   if (x > 1 && !a[x - 1][y]) {
     88     int fx = get(ha[now], now), fy = get(ha[now], now - m);
     89     if (fx != fy) {
     90       if (!fx || !fy) ha[now][fx + fy] = 0;
     91       else  ha[now][fx] = fy;
     92       hole[now]--;
     93     }
     94   }
     95   if (y==1 || y==m || x == 1 || x == n) {
     96     int fx = get(ha[now], now);
     97     if (fx) {
     98       ha[now][fx] = 0; hole[now]--;
     99     }
    100   }
    101  
    102   int flag = 1;
    103   if (y > 1 && !a[x][y - 1]) {
    104     int fx = get(ga[now], now), fy = get(ga[now], now - 1);
    105     if (fx != fy) { 
    106       ga[now][fx] = fy; 
    107       if ((sa[now][fy] += sa[now][fx]) > 1) flag = 0;
    108     }
    109   }
    110   if (x > 1 && !a[x - 1][y]) {
    111     int fx = get(ga[now], now), fy = get(ga[now], now - m);
    112     if (fx != fy) {
    113       ga[now][fx] = fy;
    114       if ((sa[now][fy] += sa[now][fx]) > 1) flag = 0;
    115     }
    116   }
    117   if (flag) dfs(now + 1, cnt, con);
    118  
    119   if (s[x][y] == 'O') return;
    120   rep(i, 1, n*m) {
    121     fa[now][i] = fa[now - 1][i];
    122     ga[now][i] = ga[now - 1][i];
    123     sa[now][i] = sa[now - 1][i];
    124     ha[now][i] = ha[now - 1][i];
    125   }
    126   hole[now] = hole[now - 1];
    127   a[x][y] = 1;
    128   con++;
    129   if (y > 1 && a[x][y-1]) {
    130     int fx = get(fa[now], now), fy = get(fa[now], now - 1);
    131     if (fx != fy) { fa[now][fx] = fy; con--; }
    132   }
    133   if (x > 1 && a[x-1][y]) {
    134     int fx = get(fa[now], now), fy = get(fa[now], now - m);
    135     if (fx != fy) { fa[now][fx] = fy; con--; }
    136   }
    137   dfs(now + 1, cnt + 1, con);
    138   a[x][y] = 0;
    139 }
    140  
    141 int main() {
    142   scanf("%d%d%d%d", &n, &m, &t, &h);
    143   rep(i, 1, n) scanf("%s", s[i] + 1);
    144   rep(i, 1, n) rep(j, 1, m) {
    145     fa[0][i*m - m + j] = i*m - m + j;
    146     ga[0][i*m - m + j] = i*m - m + j;
    147     ha[0][i*m - m + j] = i*m - m + j;
    148     sa[0][i*m - m + j] = s[i][j] == 'O';
    149     hole[0] = 0;
    150   }
    151   ans = 0;
    152   dfs(1, 0, 0);
    153   printf("%d
    ", ans);
    154   return 0;
    155 }
    诚者,君子之所守也。
  • 相关阅读:
    hdu5081
    hdu5079
    hdu5076
    hdu5072
    codeforces 739E
    codeforces 739D
    2017.2其他简要题解
    spring事务传播回滚策略
    mybatis一级缓存和二级缓存
    spring-boot-mybatis-starter工作原理
  • 原文地址:https://www.cnblogs.com/SkystarX/p/12285778.html
Copyright © 2011-2022 走看看