题目传送门: POJ 1753

给一个4 * 4的网格,每个格子中放白棋子或者黑棋子。

定义一个翻转操作,白子变黑子,黑子变白子。

每次可以对棋子进行一个操作,若操作的棋子是第i行第j列,则(i,j) (i - 1, j) (i + 1, j) (i, j - 1) (i, j +1)均进行翻转,越界的棋子就不翻转了。

最后问操作至全白或全黑的最小操作数。

具体就是一个不难的枚举题。

具体枚举方法是先对第一行进行操作(共16种)。

以后每一行操作,使上一行全为白或全为黑。

最后如果最后一行不满足全为白或黑,就无法达到操作要求,否则可以达到要求。

###Code

POJ 1753
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
//By Brickgao
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <cstdlib>
#include <algorithm>
#include <vector>
using namespace std;

char rec[6][6], map[6][6];
int num, wdo[20], bdo[20];

int oneflip(int a, int b)
{
if(rec[a][b] == 'b') rec[a][b] = 'w';
else rec[a][b] = 'b';
return 0;
}

int flip(int a, int b)
{
oneflip(a, b);
oneflip(a - 1, b);
oneflip(a + 1, b);
oneflip(a, b + 1);
oneflip(a, b - 1);
return 0;
}

int makeblack()
{
int ans = 0, flag = false;
for(int i = 2; i <= 4; i++)
for(int j = 1; j <= 4; j++)
if(rec[i - 1][j] == 'w')
{
flip(i, j);
ans ++;
}
for(int i = 1; i <= 4; i++)
if(rec[4][i] == 'w')
flag = true;
if(flag)
ans = 9999;
return ans;
}

int makewhite()
{
int ans = 0, flag = false;
for(int i = 2; i <= 4; i++)
for(int j = 1; j <= 4; j++)
if(rec[i - 1][j] == 'b')
{
flip(i, j);
ans ++;
}
for(int i = 1; i <= 4; i++)
if(rec[4][i] == 'b')
flag = true;
if(flag)
ans = 9999;
return ans;
}

void reset()
{
for(int i = 0; i <= 5; i++)
for(int j = 0; j <= 5; j++)
rec[i][j] = map[i][j];
}

int main()
{
int ans, num = 0;
memset(map, 'b', sizeof(map));
for(int i = 1; i <= 4; i++)
{
for(int j = 1; j <= 4; j++)
scanf("%c", &map[i][j]);
getchar();
}
reset();
bdo[num] = makeblack();
reset();
wdo[num] = makewhite();
num ++;
for(int i = 1; i <= 4; i ++)
{
reset();
flip(1, i);
bdo[num] = makeblack() + 1;
reset();
flip(1, i);
wdo[num] = makewhite() + 1;
num ++;
}
for(int i = 1; i <= 3; i ++)
for(int j = i + 1; j <= 4; j ++)
{
reset();
flip(1, i);
flip(1, j);
bdo[num] = makeblack() + 2;
reset();
flip(1, i);
flip(1, j);
wdo[num] = makewhite() + 2;
num ++;
}
for(int i = 1; i <= 4; i ++)
{
reset();
for(int j = 1; j <= 4; j++)
if(j != i)
flip(1 , j);
bdo[num] = makeblack() + 3;
reset();
for(int j = 1; j <= 4; j++)
if(j != i)
flip(1 , j);
wdo[num] = makewhite() + 3;
num ++;
}
reset();
for(int i = 1; i <= 4; i ++)
flip(1, i);
wdo[num] = makewhite() + 4;
reset();
for(int i = 1; i <= 4; i ++)
flip(1, i);
bdo[num] = makeblack() + 4;
ans = 9999;
for(int i = 0; i <= 15; i++)
{
if(ans > bdo[i]) ans = bdo[i];
if(ans > wdo[i]) ans = wdo[i];
}
if(ans >= 9999) printf("Impossible\n");
else
printf("%d\n", ans);
return 0;
}