因为有对步数的限制,这个题可以直接暴力dfs。
需要注意的是,在选择方向的时候才加一个步数。能撞墙的前提得是,这个球是运动的。
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn = 20 + 5;
bool G[maxn][maxn];
int r, c;
struct node
{
int x, y;
node(int a, int b): x(a), y(b) {}
node()
{
x = y = 0;
}
} s, g;
int ans;
int dir[][2] = {{-1, 0}, {0, 1}, {1, 0}, {0, -1}};
bool is_right(int x, int y)
{
if(x <= r && x>= 1 && y <= c && y >= 1) return true;
return false;
}
void dfs(int x, int y, int m, int d)
{
if(m > 10) return;
//printf("%d %d %d\n", x, y, d);
if(x == g.x && y == g.y) {ans = min(ans, m); return;}
if(d == -1)
{
for(int i = 0; i < 4; i++)
{
int tx = x + dir[i][0];
int ty = y + dir[i][1];
if(is_right(tx, ty))
{
if(!G[tx][ty]) dfs(tx, ty, m + 1, i);
}
}
}
else
{
int tx = x + dir[d][0];
int ty = y + dir[d][1];
if(is_right(tx, ty))
{
if(G[tx][ty])
{
G[tx][ty] = 0;
dfs(x, y, m, -1);
G[tx][ty] = 1;
}
else dfs(tx, ty, m, d);
}
}
}
int main()
{
while(scanf("%d%d", &c, &r) == 2 && r && c)
{
memset(G, 0, sizeof(G));
for(int i = 1; i <= r; i++)
{
for(int j = 1; j <= c; j++)
{
int t;
scanf("%d", &t);
if(t == 2) s = node(i, j);
else if(t == 3) g = node(i, j);
if(t == 1) G[i][j] = 1;
}
}
ans = maxn * maxn;
dfs(s.x, s.y, 0, -1);
printf("%d\n", ans == maxn * maxn ? -1 : ans);
}
return 0;
}