zoukankan      html  css  js  c++  java
  • poj1681 高斯消元

    Painter's Problem
    Time Limit: 1000MS   Memory Limit: 10000K
    Total Submissions: 5352   Accepted: 2588

    Description

    There is a square wall which is made of n*n small square bricks. Some bricks are white while some bricks are yellow. Bob is a painter and he wants to paint all the bricks yellow. But there is something wrong with Bob's brush. Once he uses this brush to paint brick (i, j), the bricks at (i, j), (i-1, j), (i+1, j), (i, j-1) and (i, j+1) all change their color. Your task is to find the minimum number of bricks Bob should paint in order to make all the bricks yellow. 

    Input

    The first line contains a single integer t (1 <= t <= 20) that indicates the number of test cases. Then follow the t cases. Each test case begins with a line contains an integer n (1 <= n <= 15), representing the size of wall. The next n lines represent the original wall. Each line contains n characters. The j-th character of the i-th line figures out the color of brick at position (i, j). We use a 'w' to express a white brick while a 'y' to express a yellow brick.

    Output

    For each case, output a line contains the minimum number of bricks Bob should paint. If Bob can't paint all the bricks yellow, print 'inf'.

    Sample Input

    2
    3
    yyy
    yyy
    yyy
    5
    wwwww
    wwwww
    wwwww
    wwwww
    wwwww
    

    Sample Output

    0
    15


    题意:

    一个n*n 的木板,每个格子都可以染成白色和黄色,一旦我们对某个格子染色,其上下左右都将改变颜色

    求将所有的格子染成黄色最少需要几次,若不能则输出inf。

    当有多个自由变元时,需要进行枚举求出最小值

      1 /*
      2 poj1681
      3 类似于一元开关问题。把二维矩阵转换成一维矩阵来看。
      4 在求出答案之后,对于有很多解的考虑枚举自由变元来求解
      5 最小值
      6 */
      7 #include <iostream>
      8 #include <cstdio>
      9 #include <cstdlib>
     10 #include <cstring>
     11 #include <algorithm>
     12 #include <cmath>
     13 using namespace std;
     14 typedef long long ll;
     15 typedef long double ld;
     16 
     17 using namespace std;
     18 const int maxn = 300;
     19 
     20 int equ,var;
     21 int a[maxn][maxn];
     22 int x[maxn];
     23 int free_x[maxn];
     24 int free_num;
     25 
     26 int Gauss()
     27 {
     28     int max_r,col,k;
     29     free_num = 0;
     30     for(k = 0,col = 0; k < equ && col < var; k++,col++)
     31     {
     32         max_r = k;
     33         for(int i = k+1; i < equ; i++)
     34         {
     35             if(abs(a[i][col]) > abs(a[max_r][col]))
     36                 max_r = i;
     37         }
     38         if(a[max_r][col] == 0)
     39         {
     40             k --;
     41             free_x[free_num++] = col;
     42             continue;
     43         }
     44         if(max_r != k)
     45         {
     46             for(int j = col; j < var+1; j++)
     47                 swap(a[k][j],a[max_r][j]);
     48 
     49         }
     50         for(int i = k + 1; i < equ; i++)
     51         {
     52             if(a[i][col] != 0)
     53             {
     54                 for(int j = col; j < var+1; j++)
     55                     a[i][j] ^= a[k][j];
     56             }
     57         }
     58 
     59     }
     60     for(int i = k; i < equ; i++)
     61         if(a[i][col] != 0)
     62             return -1;
     63     if(k < var) return var-k;
     64 
     65     for(int i = var-1; i >= 0; i--)
     66     {
     67         x[i] = a[i][var];
     68         for(int j = i +1; j < var; j++)
     69             x[i] ^= (a[i][j] && x[j]);
     70 
     71     }
     72     return 0;
     73 
     74 }
     75 
     76 int n;
     77 void ini()
     78 {
     79     memset(a,0,sizeof(a));
     80     memset(x,0,sizeof(x));
     81     equ = n*n;
     82     var = n*n;
     83     for(int i = 0;i < n;i++)
     84     {
     85         for(int j = 0;j < n;j++)
     86         {
     87             int tt = i*n+ j;
     88             a[tt][tt] =1;
     89             if(i > 0) a[(i-1)*n+j][tt] = 1;
     90             if(i < n-1) a[(i+1)*n+j][tt] = 1;
     91             if(j > 0) a[tt-1][tt] = 1;
     92             if(j < n-1) a[tt+1][tt] =1;
     93         }
     94     }
     95 }
     96 
     97 char str[30][30];
     98 /*
     99 2
    100 3
    101 yyy
    102 yyy
    103 yyy
    104 5
    105 wwwww
    106 wwwww
    107 wwwww
    108 wwwww
    109 wwwww
    110 */
    111 int main()
    112 {
    113     int T;
    114     char color;
    115     scanf("%d",&T);
    116     while(T--)
    117     {
    118         scanf("%d",&n);
    119         ini();
    120         for(int i = 0; i < n; i++)
    121         {
    122             scanf("%s",str[i]);
    123             for(int j = 0; j < n; j++)
    124             {
    125                 if(str[i][j] == 'y')
    126                     a[i*n+j][n*n] = 0;
    127                 else
    128                     a[i*n+j][n*n] = 1;
    129             }
    130         }
    131         int t = Gauss();
    132         if(t == -1)
    133         {
    134             printf("inf
    ");
    135         }
    136         else if(t == 0)
    137         {
    138             int ans = 0;
    139             for(int i = 0; i < n*n; i++)
    140                 ans += x[i];
    141             printf("%d
    ",ans);
    142         }
    143         else
    144         {
    145             int ans = 0x3f3f3f3f;
    146             int tot = (1 << t);
    147             for(int i = 0; i < tot; i++)
    148             {
    149                 int cnt = 0;
    150                 for(int j = 0; j < t; j++)
    151                 {
    152                     if(i & (1 << j))
    153                     {
    154                         cnt ++;
    155                         x[free_x[j]]= 1;
    156                     }
    157                     else x[free_x[j]]= 0;
    158                 }
    159 
    160                 for(int j = var-t-1; j >= 0; j--)
    161                 {
    162                     int dex;
    163                     for(dex = j; dex < var; dex++)
    164                         if(a[j][dex])
    165                             break;
    166                     x[dex] = a[j][var];
    167                     for(int l = dex +1; l <var ; l++)
    168                     {
    169                         if(a[j][l])
    170                             x[dex] ^= x[l];
    171                     }
    172                     cnt += x[dex];
    173                 }
    174                 ans = min(ans,cnt);
    175             }
    176             printf("%d
    ",ans);
    177         }
    178     }
    179     return 0;
    180 }



  • 相关阅读:
    迷宫城堡 HDU
    Strategic game POJ
    Warm up HDU
    Network POJ
    Delphi Tstream 流
    Delphi 获得文件大小的五种方法
    Delphi Messagebox 介绍
    delphi idftp
    Delphi 操作Excel
    Delphi 打印对象 Tprinter 常用属性、方法、函数、打印示例
  • 原文地址:https://www.cnblogs.com/Przz/p/5409645.html
Copyright © 2011-2022 走看看