题目:
给定一个4*4的棋盘和棋盘上所呈现出来的纸张边缘,问能否用不超过6张纸,搞出这种情况。
要点:
无, 测试数据很水,不用担心超时
在我自己的电脑上运行肯定超过3s了,那些测试样例。。
但是110ms过了
代码有点长,但是非常好理解,都注释了。
#include
#define LL long long
using namespace std;
int pic[5][10]; //定义原始图形
int p[5][10]; //之后的图形
/*
0表示 " "
1表示 "_"
2表示 "|"
一个正方形的填充区域
01010
20002
21012
*/
bool vis[10];
bool read() {
memset(pic, 0, sizeof(pic));
memset(p, 0, sizeof(p));
memset(vis, 0, sizeof(vis));
//五行 7列
for (int i = 0; i < 5; i++) {
for (int j = 0; j < 10; j++) {
char ch;
ch = cin.get();
if (ch == '0') return false;
if (isspace(ch)) {
pic[i][j] = 0;
}
else if (ch == '_') {
pic[i][j] = 1;
}
else if (ch == '|') {
pic[i][j] = 2;
}
else {
cin.get(); //读掉换行
break;
}
}
}
// for(int i = 0; i < 5; i++) {
// for(int j = 0; j < 10; j++) {
// cout << pic[i][j];
// }
// cout << endl;
// }
return true;
}
//定义偏移量
int offx[] = { 0, 1, 2 };
int offy[] = { 0, 1, 2 };
string s[3] = { "01010", "20002", "21012" };
//放置 0 - 8 个图形
//返回原来的情况
vector<string> put(int num1) {
int ox = num1 / 3;
int oy = num1 % 3;
vector<string> ss;
ss.resize(5);
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 5; j++) {
ss[i].push_back(p[i + ox][j + oy * 2]);
if (i == 0 && s[i][j] == '0') continue;
p[i + ox][j + oy * 2] = s[i][j] - '0';
}
}
return ss;
}
//回溯用
void reset(int num1, vector<string> ss) {
int ox = num1 / 3;
int oy = num1 % 3;
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 5; j++) {
if (i == 0 && s[i][j] == '0') continue;
p[i + ox][j + oy * 2] = ss[i][j];
}
}
}
bool check() {
for (int i = 0; i < 5; i++) {
for (int j = 0; j < 10; j++) {
if (pic[i][j] != p[i][j]) return false;
}
}
return true;
}
//搜索与回溯
bool dfs(int d, int maxd) {
//cout << "d: " << d << endl;
//for(int i = 0; i < 5; i++) {
// for(int j = 0; j < 10; j++) {
// //cout << p[i][j];
// if (p[i][j] == 0) cout << " ";
// if (p[i][j] == 1) cout << "_";
// if (p[i][j] == 2) cout << "|";
// }
// cout << endl;
//}
//cout << endl;
if (d == maxd) {
if (check())
return true;
return false;
}
if (check()) return true;
for (int i = 0; i < 9; i++) {
if (vis[i]) continue;
vis[i] = true;
vector<string> ss = put(i);
if (dfs(d + 1, maxd))
return true;
reset(i, ss);
vis[i] = false;
}
return false;
}
int main() {
// freopen("in.txt", "r", stdin);
// freopen("out.txt", "w", stdout);
ios::sync_with_stdio(false);
cin.tie(0);
int kase = 0;
while (read()) {
cout << "Case " << ++kase << ": ";
if (check() || dfs(0, 6)) {
cout << "Yes" << endl;
continue;
}
cout << "No" << endl;
}
return 0;
}