双向BFS
棋盘上有四个棋子,给你两个状态,问可否8步内将一个状态转移到另一个状态。双向BFS。
偶这题写了一晚加一个下午,一开始兴致勃勃地单向BFS,当TLE后才发现状态总数估计错误了,应该是(4*4)^8。以后这样的错误要避免撒~~~~
然后判重时用 int mark[8][8][8][8][8][8][8][8],一交,超内存了,再次悲剧。其实这样的话内存耗费是(8^8)*4/1024 = 65536K,明显要超的~~~~~
#include <iostream>
#include <queue>
#include <algorithm>
using namespace std;
struct Node { int x, y; };
struct Status { Node nd[4]; int deep;};
char mark[8][8][8][8][8][8][8][8];
int dir[4][2] = { 0, -1, -1, 0, 0, 1, 1, 0 };
Status _s;
queue<Status> Q1, Q2;
bool cmp( Node n1, Node n2 ) {
if( n1.x != n2.x ) return n1.x < n2.x;
else return n1.y < n2.y;
}
void Mark( Status s1, int v ) {
v --;
mark[s1.nd[0].x][s1.nd[0].y][s1.nd[1].x][s1.nd[1].y][s1.nd[2].x][s1.nd[2].y][s1.nd[3].x][s1.nd[3].y] |= (1<<v);
}
void init() {
int i;
memset( mark, 0, sizeof(mark) );
for( i=1; i<4; ++i ) {
scanf( "%d %d", &_s.nd[i].x, &_s.nd[i].y );
}
for( i=0; i<4; ++i ) {
_s.nd[i].x --; _s.nd[i].y --;
}
sort( _s.nd, _s.nd+4, cmp );
while( !Q1.empty() ) Q1.pop();
while( !Q2.empty() ) Q2.pop();
_s.deep = 0;
Q1.push( _s );
Mark( _s, 1 );
for( i=0; i<4; ++i ) {
scanf( "%d %d", &_s.nd[i].x, &_s.nd[i].y );
_s.nd[i].x --; _s.nd[i].y --;
}
sort( _s.nd, _s.nd+4, cmp );
_s.deep = 0;
Q2.push( _s );
Mark( _s, 2 );
}
bool occupy( Status _p, int v, Status _q ) {
for( int i=0; i<4; ++i ) {
if( _p.nd[v].x == _q.nd[i].x && _p.nd[v].y == _q.nd[i].y ) return 1;
}
return 0;
}
bool isVisited( Status s1, int v ) {
v --;
if( mark[s1.nd[0].x][s1.nd[0].y][s1.nd[1].x][s1.nd[1].y][s1.nd[2].x][s1.nd[2].y][s1.nd[3].x][s1.nd[3].y] &(1<<v) ) return 1;
return 0;
}
bool solve() {
int i, j;
Status _p, _q;
while( !Q1.empty() || !Q2.empty() ) {
if( !Q1.empty() ) {
_p = Q1.front();
Q1.pop();
if( _p.deep >= 4 ) continue;
for( i=0; i<4; ++i ) {
for( j=0; j<4; ++j ) {
_q = _p;
_q.deep ++;
_q.nd[i].x += dir[j][0];
_q.nd[i].y += dir[j][1];
if( _q.nd[i].x < 0 || _q.nd[i].y < 0 || _q.nd[i].x >= 8 || _q.nd[i].y >= 8) continue;
if( occupy(_q, i, _p) ) {
_q.nd[i].x += dir[j][0];
_q.nd[i].y += dir[j][1];
}
if( _q.nd[i].x < 0 || _q.nd[i].y < 0 || _q.nd[i].x >= 8 || _q.nd[i].y >= 8 || occupy(_q, i, _p)) continue;
sort( _q.nd, _q.nd+4, cmp );
if( isVisited( _q, 1 ) ) continue;
if( isVisited( _q, 2 ) ) return 1;
Q1.push( _q );
Mark( _q, 1 );
}
}
}
if( !Q2.empty() ) {
_p = Q2.front();
Q2.pop();
if( _p.deep >= 4 ) continue;
for( i=0; i<4; ++i ) {
for( j=0; j<4; ++j ) {
_q = _p;
_q.deep ++;
_q.nd[i].x += dir[j][0];
_q.nd[i].y += dir[j][1];
if( _q.nd[i].x < 0 || _q.nd[i].y < 0 || _q.nd[i].x >= 8 || _q.nd[i].y >= 8) continue;
if( occupy(_q, i, _p) ) {
_q.nd[i].x += dir[j][0];
_q.nd[i].y += dir[j][1];
}
if( _q.nd[i].x < 0 || _q.nd[i].y < 0 || _q.nd[i].x >= 8 || _q.nd[i].y >= 8 || occupy(_q, i, _p) ) continue;
sort( _q.nd, _q.nd+4, cmp );
if( isVisited( _q, 2 ) ) continue;
if( isVisited( _q, 1 ) ) return 1;
Q2.push( _q );
Mark( _q, 2 );
}
}
}
}
return 0;
}
int main() {
// freopen( "c:/aaa.txt", "r", stdin );
while( scanf("%d %d", &_s.nd[0].x, &_s.nd[0].y ) == 2 ) {
init();
solve() ? puts( "YES" ) : puts( "NO" );
}
return 0;
}
.
浙公网安备 33010602011771号