棋盘状态有2的16次方种,可以通过二进制状态压缩来表示棋盘状态,进行判重。

TLE了一次,我用的STL的队列,自己实现队列后32MS过掉。

 

  #include <iostream>

#include <cstring>
#include 
<cstdio>
#include 
<queue>
using namespace std;
struct state
{
    
int s;
    
int step;
    state()
    {
    }
    state(
int ss,int sstep):s(ss),step(sstep)
    {
    }
};
state q[
1<<16];
bool mark[1<<16+1];
char str[6];
state s;
int dx[4]={0,1,-1,0};
int dy[4]={1,0,0,-1};

void bfs()
{
    
int front=-1,rear = -1;
    
bool flag = false;
    q[
++rear] = s;
    
while(front<rear)
    {
        state cur 
= q[++front];
        
int ts = cur.s;
        
int tstep = cur.step;
        
if(mark[ts])
        {
            
continue;
        }
        mark[ts] 
= true;
        
if(ts==0||ts==65535)
        {
            flag 
= true;
            printf(
"%d\n",cur.step);
            
break;
        }
        
int tts;
        
for(int i=0;i<4;i++)
         
for(int j=0;j<4;j++)
         {
             tts 
= ts;
             
for(int k=0;k<4;k++)
             {
                 
int ti = i+dx[k];
                 
int tj = j+dy[k];
                 
if(ti>=0&&ti<4&&tj>=0&&tj<4)
                 {
                      tts 
^= 1<<(ti*4 + tj);
                 }
             }
             tts 
^= 1<<(i*4 + j);
             q[
++rear] = state(tts,tstep+1);
         }
    }
    
if(!flag)
    {
        printf(
"Impossible\n");
    }
}
int main()
{
     
int ts= 0;
    memset(mark,
false,sizeof(mark));
    
for(int i=0;i<4;i++)
    {
        scanf(
"%s",str);
     
for(int j=0;j<4;j++)
     {
         
if(str[j]=='b')
         {
             ts 
|= 1<<(i*4 + j);
         }
     }
    }
    s 
= state(ts,0);
    bfs();
    
return 0;
}