题意:在r*c的矩形方格地图中,有钢地板和易碎地板,分别以'.'和'E'代替。有个1*1*2的长方体,在这上面滚动,要使它最后立在目标位置上(就是只占一格且在目标上),长方体初始位置用'X'表示,目标用'O'表示。
题解:bfs,记录长方体左上角的点的位置以及它的摆放位置(立着:0,横躺着:1,竖躺着:2),然后就可以用mark[505][505][3]的bool数组记录是否走过某点了。
View Code
1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 using namespace std; 5 const int N=505,M=1000000; 6 char map[N][N]; 7 bool mark[N][N][3]; 8 int r,c; 9 struct Data 10 { 11 int x,y,w,step; 12 }S[M]; 13 bool in(int x,int y) 14 { 15 return x>=1&&x<=r&&y>=1&&y<=c; 16 } 17 bool place(int x,int y,int w) 18 { 19 if(!in(x,y)||map[x][y]=='#') 20 return false; 21 switch(w) 22 { 23 case 0: 24 return map[x][y]!='E';break; 25 case 1: 26 return in(x,y+1)&&map[x][y+1]!='#';break; 27 case 2: 28 return in(x+1,y)&&map[x+1][y]!='#';break; 29 } 30 } 31 int dr[][2]={0,1,1,0,0,-1,-1,0}; 32 int main() 33 { 34 while(scanf("%d%d",&r,&c),(r||c)) 35 { 36 bool flag=false; 37 Data a,b; 38 for(int i=1; i<=r; i++) 39 { 40 scanf("%s",map[i]+1); 41 for(int j=1; j<=c; j++) 42 { 43 if(map[i][j]=='X') 44 { 45 if(flag) 46 { 47 if(in(i-1,j)&&map[i-1][j]=='X') 48 a.w=2; 49 else 50 a.w=1; 51 } 52 else 53 { 54 flag=true; 55 a.x=i; 56 a.y=j; 57 a.w=a.step=0; 58 } 59 } 60 } 61 } 62 int st=0,ed=1; 63 S[0]=a; 64 memset(mark,false,sizeof(mark)); 65 mark[a.x][a.y][a.w]=true; 66 while(st!=ed) 67 { 68 a=S[st++]; 69 if(st==M) 70 st=0; 71 if(a.w==0&&map[a.x][a.y]=='O') 72 { 73 flag=false; 74 printf("%d\n",a.step); 75 break; 76 } 77 for(int i=0;i<4;i++) 78 { 79 b.x=a.x+dr[i][0]; 80 b.y=a.y+dr[i][1]; 81 b.step=a.step+1; 82 switch(a.w) 83 { 84 case 0: 85 { 86 switch(i) 87 { 88 case 0: 89 b.w=1;break; 90 case 1: 91 b.w=2;break; 92 case 2: 93 b.w=1;b.y--;break; 94 case 3: 95 b.w=2;b.x--;break; 96 } 97 break; 98 } 99 case 1: 100 { 101 switch(i) 102 { 103 case 0: 104 b.w=0;b.y++;break; 105 case 1: 106 b.w=1;break; 107 case 2: 108 b.w=0;break; 109 case 3: 110 b.w=1;break; 111 } 112 break; 113 } 114 case 2: 115 { 116 switch(i) 117 { 118 case 0: 119 b.w=2;break; 120 case 1: 121 b.x++;b.w=0;break; 122 case 2: 123 b.w=2;break; 124 case 3: 125 b.w=0;break; 126 } 127 break; 128 } 129 } 130 if(place(b.x,b.y,b.w)&&!mark[b.x][b.y][b.w]) 131 { 132 mark[b.x][b.y][b.w]=true; 133 S[ed++]=b; 134 if(ed==M) 135 ed=0; 136 } 137 } 138 } 139 if(flag) 140 printf("Impossible\n"); 141 } 142 return 0; 143 }