5208. 穿过迷宫的最少移动次数
显示英文描述
- 用户通过次数45
- 用户尝试次数84
- 通过次数48
- 提交次数145
- 题目难度Hard
你还记得那条风靡全球的贪吃蛇吗?
我们在一个 n*n
的网格上构建了新的迷宫地图,蛇的长度为 2,也就是说它会占去两个单元格。蛇会从左上角((0, 0)
和 (0, 1)
)开始移动。我们用 0
表示空单元格,用 1 表示障碍物。蛇需要移动到迷宫的右下角((n-1, n-2)
和 (n-1, n-1)
)。
每次移动,蛇可以这样走:
- 如果没有障碍,则向右移动一个单元格。并仍然保持身体的水平/竖直状态。
- 如果没有障碍,则向下移动一个单元格。并仍然保持身体的水平/竖直状态。
- 如果它处于水平状态并且其下面的两个单元都是空的,就顺时针旋转 90 度。蛇从(
(r, c)
、(r, c+1)
)移动到 ((r, c)
、(r+1, c)
)。 - 如果它处于竖直状态并且其右面的两个单元都是空的,就逆时针旋转 90 度。蛇从(
(r, c)
、(r+1, c)
)移动到((r, c)
、(r, c+1)
)。
返回蛇抵达目的地所需的最少移动次数。
如果无法到达目的地,请返回 -1
。
示例 1:
输入:grid = [[0,0,0,0,0,1], [1,1,0,0,1,0], [0,0,0,0,1,1], [0,0,1,0,1,0], [0,1,1,0,0,0], [0,1,1,0,0,0]] 输出:11 解释: 一种可能的解决方案是 [右, 右, 顺时针旋转, 右, 下, 下, 下, 下, 逆时针旋转, 右, 下]。
示例 2:
输入:grid = [[0,0,1,1,1,1], [0,0,0,0,1,1], [1,1,0,0,0,1], [1,1,1,0,0,1], [1,1,1,0,0,1], [1,1,1,0,0,0]] 输出:9
提示:
2 <= n <= 100
0 <= grid[i][j] <= 1
- 蛇保证从空单元格开始出发。
思路:辣鸡题一道,典型的BFS题,我们可以定义一个node类标记状态,其中状态无非就是蛇尾、蛇头坐标,当前是否是水平或者垂直,已经走到当前状态的步骤。flag数组表示蛇尾坐标为x,y并且当前是水平或者垂直的状态是否已经遍历过。
class Solution {
class node
{
int x1,x2,y1,y2,state,step;
public node(int x1,int y1,int x2,int y2,int state,int step)
{
this.x1=x1;
this.y1=y1;
this.x2=x2;
this.y2=y2;
this.state=state;
this.step=step;
}
}
boolean[][][] flag=new boolean[105][105][2];
public int minimumMoves(int[][] grid) {
int n=grid.length;
node start=new node(0,0,0,1,0,0); flag[0][0][0]=true;
node end=new node(n-1,n-2,n-1,n-1,0,0);
Queue<node> q=new LinkedList();
q.add(start);
while(!q.isEmpty())
{
node now=q.poll();
if(isOk(now,end))
return now.step;
int dx1,dy1,dx2,dy2;
if(now.state==0)
{
dx1=now.x1;dy1=now.y1+1;
dx2=now.x2;dy2=now.y2+1;
if(dy1<n && dy2<n && !flag[dx1][dy1][0] && grid[dx2][dy2]==0)
{
flag[dx1][dy1][0]=true;
q.add(new node(dx1,dy1,dx2,dy2,0,now.step+1));
}
if(dx1+1<n && grid[dx1+1][now.y1]==0 && grid[dx1+1][now.y2]==0)
{
if(!flag[dx1+1][now.y1][0])
{
flag[dx1+1][now.y1][0]=true;
q.add(new node(dx1+1,now.y1,dx2+1,now.y2,0,now.step+1));
}
if(!flag[dx1][now.y1][1])
{
flag[dx1][now.y1][1]=true;
q.add(new node(dx1,now.y1,dx1+1,now.y1,1,now.step+1));
}
}
}
else
{
dx1=now.x1+1;dy1=now.y1;
dx2=now.x2+1;dy2=now.y2;
if(dx1<n && dx2<n && grid[dx2][dy2]==0 && !flag[dx1][dy1][1])
{
flag[dx1][dy1][1]=true;
q.add(new node(dx1,dy1,dx2,dy2,1,now.step+1));
}
if(dy1+1<n && grid[now.x1][now.y1+1]==0 && grid[now.x2][now.y2+1]==0)
{
if(!flag[now.x1][now.y1+1][1])
{
flag[now.x1][now.y1+1][1]=true;
q.add(new node(now.x1,now.y1+1,now.x2,now.y2+1,1,now.step+1));
}
if(!flag[now.x1][now.y1][0])
{
flag[now.x1][now.y1][0]=true;
q.add(new node(now.x1,now.y1,now.x1,now.y1+1,0,now.step+1));
}
}
}
}
return -1;
}
private boolean isOk(node a,node b)
{
if(a.x1==b.x1 && a.x2==b.x2 && a.y1==b.y1 && a.y2==b.y2)
return true;
return false;
}
}