zoukankan      html  css  js  c++  java
  • poj1222 EXTENDED LIGHTS OUT

    设输入矩阵为A,输出矩阵为B,目标矩阵为C(零矩阵)。

    方便起见,矩阵行列下标均从1开始。

    考虑A矩阵元素a(i,j),B矩阵中与其相邻的元素 b(i,j),b(i - 1, j),b(i + 1,j),b(i,j - 1),b(i,j + 1) (#)。

    有c(i,j)= 0 = a(i,j) ^ (∑ b(i,j) % 2)。

    进一步有a(i,j) ^ 0 = a(i,j) = a(i,j) ^ a(i,j) ^ (∑ b(i,j) % 2) = ∑ b(i,j) % 2     (*)。

    进一步考虑异或与模2加之间的关系:∑ b(i,j) % 2 = ^ B(i, j),其中B(i,j)表示(#)式5个元素的集合。

    带入(*):^ B(i, j) = a(i,j)。这是我们需要的方程组。

    (注:考虑边界上的元素,只需将不在矩阵范围内的b元素全部置零即可。)

    将b(i,j)映射到x((i - 1) * 5 + j)(x下标从1到5 * 6)。

    下面考虑解异或方程组AX= B。(与前面的表达无关)

    a11 * x1 ^ a12 * x2 ^...^ a1n * xn = b1 ①

    ...

    an1 * x1 ^ an2 * x2 ^...^ann * xn = bn ②

    A,X,B均为0-1矩阵。

    考虑消元,现在看系数矩阵A的第一列,若全部元素均为0,直接转到下一列,并且有方程组有多解。

    若存在ai1 = 1,将其与第一行交换(这样做的目的是为了得到上三角阵)。

    此时只需考虑剩余所有 1 < j ≤ n, 且aj1 = 1。有:

    a11 * x1 ^ a12 * x2 ^...^ a1n * xn = b1 ①

    aj1 * x1 ^ aj2 * x2 ^...^ ajn * xn = bj ②

    ① ^ ②:

    (a11 * x1 ^ a12 * x2 ^...^ a1n * xn) ^ (aj1 * x1 ^ aj2 * x2 ^...^ ajn * xn) = b1 ^ bj。

    即:(a11 * x1 ^ aj1 * x1) ^ (a12 * x2 ^ aj2 * x2) ^...^ (a1n * xn ^ ajn * xn) = b1 ^ bj 。

    易于验证:a * x ^ b ^ x = (a ^ b) * x,因此进一步有:

    (a11 ^ aj1)*x1 ^ (a12 ^ aj2)*x2  ^ .... ^ (a1n ^ ajn)*xn = b1 ^ bj 。

    因而第j行x1的系数更新为1 ^ 1 即0 。 

    对增广阵如此消元至得到上三角阵即可得到答案。

    http://poj.org/problem?id=1222

     1 #include <cstdio>
     2 #include <cstring>
     3 #include <algorithm>
     4 using namespace std;
     5 const int maxx = 5;
     6 const int maxy = 6;
     7 const int maxm = maxx * maxy;
     8 const int maxn = maxm + 10;
     9 int A[maxn][maxn], B[maxn];
    10 int C[maxn][maxn];
    11 int dx[] = {0, 0, 0, -1, 1};
    12 int dy[] = {0, -1, 1, 0, 0};
    13 int pos(int i, int j) { return (i - 1) * maxy + j; }
    14 bool in_range(int i, int j) { return i >= 1 && i <= maxx && j >= 1 && j <= maxy; }
    15 void solve(){
    16     memset(C, 0, sizeof C);
    17     for(int i = 1, k = 1; i <= maxx; i++) for(int j = 1; j <= maxy; j++, k++){
    18         //the k-th column of the coefficient matrix
    19         for(int u = 0; u < 5; u++){
    20             int nx = i + dx[u], ny = j + dy[u], p = pos(nx, ny);
    21             if(in_range(nx, ny)) C[k][p] = 1;
    22         }
    23         C[k][maxm + 1] = A[i][j];
    24     }
    25     for(int i = 1; i <= maxm; i++){
    26         //eliminate for X(i)
    27         for(int j = i; j <= maxm; j++){
    28             //highlighting A[j][]
    29             if(C[j][i]){
    30                 swap(C[i], C[j]);
    31                 break;
    32             }
    33         }
    34         for(int j = i + 1; j <= maxm; j++){
    35             if(!C[j][i]) continue;
    36             for(int k = i; k <= maxm + 1; k++) C[j][k] ^= C[i][k];
    37         }
    38     }
    39     //retrieve the ans
    40     for(int i = maxm; i >= 1; i--){
    41         B[i] = C[i][maxm + 1];
    42         for(int j = i + 1; j <= maxm; j++) if(C[i][j]) B[i] ^= B[j];
    43     }
    44     for(int i = 1; i <= maxx; i++){
    45         printf("%d", B[pos(i, 1)]);
    46         for(int j = 2; j <= maxy; j++){
    47             int p = pos(i, j);
    48             printf(" %d", B[p]);
    49         }
    50         printf("
    ");
    51     }
    52 }
    53 
    54 int main(){
    55     freopen("in.txt", "r", stdin);
    56     int T, kase = 0;
    57     scanf("%d", &T);
    58     while(T--){
    59         printf("PUZZLE #%d
    ", ++kase);
    60         for(int i = 1; i <= maxx; i++) for(int j = 1; j <= maxy; j++) scanf("%d", &A[i][j]);
    61         solve();
    62     }
    63     return 0;
    64 }
    View Code
  • 相关阅读:
    how to uninstall devkit
    asp.net中bin目录下的 dll.refresh文件
    查找2个分支的共同父节点
    Three ways to do WCF instance management
    WCF Concurrency (Single, Multiple, and Reentrant) and Throttling
    检查string是否为double
    How to hide TabPage from TabControl
    获取当前系统中的时区
    git svn cygwin_exception
    lodoop打印控制具体解释
  • 原文地址:https://www.cnblogs.com/astoninfer/p/4830131.html
Copyright © 2011-2022 走看看