【暴力枚举&BFS】Flow Free @RMRC2017/upcexam5124
时间限制: 1 Sec 内存限制: 128 MB
题目描述
Flow Free is a puzzle that is played on a 2D grid of cells, with some cells marked as endpoints of certain colors and the rest of cells being blank. To solve the puzzle, you have to connect each pair of colored endpoints with a path, following these rules:
there is a path connecting two points with the same color, and that path also has that color
all cells in the grid are used and each cell belongs to exactly one path (of the same color as the endpoints of the path)
The rules imply that different colored paths cannot intersect.
The path is defined as a connected series of segments where each segment connects two neighbouring cells. Two cells are neighbours if they share a side (so all segments are either horizontal or vertical). By these definitions and rules above, each colored cell will be an endpoint of exactly one segment and each blank cell will be an endpoint of exactly two segments.
In this problem we will consider only the 4×4 puzzle, with 3 or 4 pairs of colored endpoints given.
Your task is to determine if a given puzzle is solvable or not.
输入
The input consists of 4 lines, each line containing 4 characters. Each character is from the set {R, G,B, Y,W}whereW denotes the blank cells and the other characters denote endpoints with the specified color. You are guaranteed that there will be exactly 3 or 4 pairs of colored cells. If there are 3 colors in the grid, Y will be omitted.
输出
On a single line output either “solvable” or “not solvable” (without the quotes).
样例输入
RGBW
WWWW
RGBY
YWWW
样例输出
solvable
开始读错了题,没注意要连上所有的块。
暴力枚举每个W块的颜色,每种情况下从起点广搜终点,不用vis数组剪枝而采用记录路径(状压)可以保证搜到每种路径,搜到终点时判断是否走过了所有相同颜色的格子。
第二天仔细想想,还是写的太麻烦了,实际上直接深搜就好了…
#define IN_LB() freopen("F:\\in.txt","r",stdin)
#define IN_PC() freopen("C:\\Users\\hz\\Desktop\\in.txt","r",stdin)
#include <bits/stdc++.h>
using namespace std;
const int dirx[] = {-1,0,1,0};
const int diry[] = {0,1,0,-1};
const char col[] ="RGBY";
char mapp[5][5];
struct node {
int x,y,route,step;
node() {}
node(int x,int y,int route,int step):x(x),y(y),route(route),step(step) {}
} cR[2],cG[2],cB[2],cY[2];
int cntR,cntG,cntB,cntY;
vector <int> v;
int xytoInd(int x,int y){
return x*4+y;
}
bool bfs(char color,node st,node ed,int cnum) {
queue<node> q;
q.push(st);
while(!q.empty()) {
int x = q.front().x,y=q.front().y,route = q.front().route,step = q.front().step;
q.pop();
if(x==ed.x&&y==ed.y&&cnum+1==step)return true;
for(int i=0; i<4; i++) {
int xx = x+dirx[i],yy=y+diry[i];
if(xx>=0&&xx<4&&yy>=0&&yy<4&&mapp[xx][yy]==color&&((route&(1<<xytoInd(xx,yy)))==0)) {
q.push(node(xx,yy,route|(1<<xytoInd(xx,yy)),step+1));
}
}
}
return false;
}
int main() {
// IN_PC();
for(int i=0; i<4; i++) {
scanf("%s",mapp[i]);
}
for(int i=0; i<4; i++) {
for(int j=0; j<4; j++) {
if(mapp[i][j]=='W') {
v.push_back(i*4+j);
}
if(mapp[i][j]=='R') {
cR[cntR++] = node(i,j,1<<xytoInd(i,j),0);
}
if(mapp[i][j]=='G') {
cG[cntG++] = node(i,j,1<<xytoInd(i,j),0);
}
if(mapp[i][j]=='B') {
cB[cntB++] = node(i,j,1<<xytoInd(i,j),0);
}
if(mapp[i][j]=='Y') {
cY[cntY++] = node(i,j,1<<xytoInd(i,j),0);
}
}
}
int num = v.size();
int flag = 0;
if(num==8) {
int sumsta = pow(4,8);
for(int i=0; i<sumsta; i++) {
int c = i,cn[4]={0};
for(int j=0; j<8; j++) {
int x = v[j]/4,y = v[j]%4;
mapp[x][y] = col[c%4];
cn[c%4]++;
c/=4;
}
if(bfs('R',cR[0],cR[1],cn[0])
&&bfs('G',cG[0],cG[1],cn[1])
&&bfs('B',cB[0],cB[1],cn[2])
&&bfs('Y',cY[0],cY[1],cn[3])) {
flag = 1;
break;
}
}
} else if(num==10) {
int sumsta = pow(3,10);
for(int i=0; i<sumsta; i++) {
int c = i,cn[3]={0};
for(int j=0; j<10; j++) {
int x = v[j]/4,y = v[j]%4;
mapp[x][y] = col[c%3];
cn[c%3]++;
c/=3;
}
if(bfs('R',cR[0],cR[1],cn[0])
&&bfs('G',cG[0],cG[1],cn[1])
&&bfs('B',cB[0],cB[1],cn[2])) {
flag = 1;
break;
}
}
}
if(flag)printf("solvable\n");
else printf("not solvable\n");
return 0;
}