Title Link: http://poj.org/problem?id=2446
Main topic:
Give you a m*n chess board, which has k a small hole, now give you 1*2 of paper, if can just cover all the lattice without holes, and each lattice can not be covered 2 times, a piece of papers must be 1*2 scale, so the output is yes.
Problem Solving Ideas:
The problem was found in the search for two points. But I can't see where I can use the maximum matching of the binary graph to do it. Had to search the puzzle ...
The idea is:
Think of the chessboard as a chess chessboard, black and white. Any 2 adjacent squares must be of different colors (black and white). After the study found that if the row and column numbers of a lattice add up to an odd number, then the row and column numbers of the adjacent lattice must be even, if the row and column numbers of a lattice add up to an even number, then the row and column numbers of the lattice adjacent to it must add up to an odd number.
In this way, we can divide the chessboard into odd and even sets. When we add the edge, we just need to add it above or to the left.
The code is as follows:
#include <iostream> #include <cstdio> #include <cstring> #include <algorithm> #include <
Cmath> using namespace std;
const int M = ~ ~, N = m * m;
int head[m], next[n], key[n], top;
int match[m];
BOOL Use[m], map[m][m];
int m, n, K;
void Add (int u, int v)//odd + even {key[top] = V;
Next[top] = Head[u];
Head[u] = top++;
} bool Find (int u) {int temp;
for (int i = head[u]; i =-1; i = Next[i]) {temp = Key[i];
if (!use[temp]) {use[temp] = true;
if (match[temp] = = 1 | | find (MATCH[TEMP])) {match[temp] = u;
return true;
}}} return false;
} int sum (int n) {int sumall = 0;
for (int i = 0; i < n; ++i) {memset (use, False, sizeof (use));
if (find (i)) sumall++;
} return SumAll;
} int main () {int x, y;
while (scanf ("%d%d%d", &m, &n, &k)! = EOF) {if ((M * n-k) & 1) {printf ("no\n");
Continue
} top = 0;
Memset (Head,-1, sizeof (head));
memset (Match,-1, sizeof (match)); memset (MAP, True, sizeof (map));
for (int i = 0; i < K; ++i) {scanf ("%d%d", &y, &x);//First y after x map[x-1][y-1] = false; } for (int i = 0, i < m; ++i) {for (int j = 0; J < N; ++j) {if (Map[i][j]) {if (i-1 >= 0
&& map[i-1][j])//on {if ((i + j) & 1) Add (I * n + j, (i-1) * n + j);
else Add ((i-1) * n + j, I * n + j); } if (j-1 >= 0 && map[i][j-1])//left {if ((i + j) & 1) Add (I * n + j, I * n + j-1
);
else Add (I * n + j-1, I * n + j); }}}} printf ("%s\n", SUM (M * N) = = ((M * n-k)/2)?
"YES": "NO");
} return 0; }