进入第二章:上来就是一个比较繁琐的图论,求迷宫的最大联通块,然后允许拆一块墙,在求一次此时的最大联通块
求联通块:dfs+枚举每一块墙, 要注意的是题目说要尽量靠西的答案,和尽量靠南的答案,那么在枚举墙的时候应
for (int j = 1; j < M; j++)
for (int i = N; i > 0; i--)
通过自底向上,从左到右枚举就省去了比较
2: 每面墙会在两个小块内被表示:那么枚举时按题目要求,每个小块只用看他的N,E墙即可。
3:由于2,要将一面墙“打破”, 将两个相邻块的bool数组置为false
/*
ID: zhangw31
PROG: castle
LANG: C++
*/
#include <iostream>
#include <fstream>
#include <cstring>
#include <algorithm>
using namespace std;
ifstream fin("castle.in");
ofstream fout("castle.out");
int M, N;
int maxspace, number, tmp, maxs;
const int MAXN = 55;
bool vis[MAXN][MAXN];
bool sta[MAXN][MAXN][4];
int posx, posy;
char direc;
void check(int i, int j, int n)
{
if (n % 2 == 1) {
sta[i][j][2] = true;
n -= 1;
}
if (n >= 8) {
sta[i][j][1] = true;
n -= 8;
}
if (n >= 4) {
sta[i][j][3] = true;
n -= 4;
}
if (n == 2) {
sta[i][j][0] = true;
}
}
void dfs(int i, int j)
{
vis[i][j] = true;
tmp ++;
if (!sta[i][j][0] && !vis[i-1][j]) dfs(i-1, j);
if (!sta[i][j][1] && !vis[i+1][j]) dfs(i+1, j);
if (!sta[i][j][2] && !vis[i][j-1]) dfs(i, j-1);
if (!sta[i][j][3] && !vis[i][j+1]) dfs(i, j+1);
}
void solve()
{
tmp = 0;
for (int i = 1; i <= N; i++) {
for (int j = 1; j <= M; j++) {
if (!vis[i][j]) {
number ++;
dfs(i, j);
if (tmp > maxspace) maxspace = tmp;
tmp = 0;
}
}
}
}
void reset()
{
for (int i = 1; i <= N; i++) {
for (int j = 1; j <= M; j++) {
vis[i][j] = false;
}
}
for (int j = 0; j <= M + 1; j++) {
vis[0][j] = true;
vis[N+1][j] = true;
}
for (int i = 0; i <= N + 1; i++) {
vis[i][0] = true;
vis[i][M+1] = true;
}
}
int main()
{
fin >> M >> N;
for (int i = 1; i <= N; i++) {
for (int j = 1; j <= M; j++) {
fin >> tmp;
check(i, j, tmp);
}
}
solve();
fout << number << endl;
fout << maxspace << endl;
for (int j = 1; j <= M; j++) {
for (int i = N; i >= 1; i--) {
if (sta[i][j][0]) {
sta[i][j][0] = sta[i-1][j][1] = false;
reset();
solve();
if (maxs < maxspace) {
maxs = maxspace;
posx = i; posy = j; direc = 'N';
}
sta[i][j][0] = sta[i-1][j][1] = true;
}
if (sta[i][j][3]) {
sta[i][j][3] = sta[i][j+1][2] = false;
reset();
solve();
if (maxs < maxspace) {
maxs = maxspace;
posx = i; posy = j; direc = 'E';
}
sta[i][j][3] = sta[i][j+1][2] = true;
}
}
}
fout << maxs << endl;
fout << posx << " " << posy << " " << direc << endl;
}