第 14 日:机器人的运动范围
题目链接:https://leetcode-cn.com/problems/ji-qi-ren-de-yun-dong-fan-wei-lcof/
题目
解题
-
深度优先搜索dfs+记录 简单
解题思路:
题目中描述是从 (0,0) 位置开始的,每次只能走一格,上下左右都行
但因为(0,0)是左上角,所以我们可以简化成走的方向只有两种:下、右;
1、往下走一格 即:(x+1,y)
2、往右走一格 即:(x,y+1)
走过的格子记忆
1、判断此格子走没走过,如果走过则return
2、如果没有走过,将此位置记录,继续dfs,往下或往右,直至不符合条件详细代码如下:
class Solution {
// 记忆数组
boolean[][] clew;
int sum;
public int movingCount(int m, int n, int k) {
clew=new boolean[m][n];
sum=0;
dfs(m,n,k,0,0);
return sum;
}
private void dfs(int m,int n,int k,int x,int y){
//判断是否溢出和已经去过
if (m==x||n==y||clew[x][y]) return;
//判断是否满足题目条件
if (get(x)+get(y)>k) return;
//记录
clew[x][y]=true;
sum++;
//向下
dfs(m,n,k,x+1,y);
//向上
dfs(m,n,k,x,y+1);
}
private int get(int x){
int s=0;
while(x>0){
s=s+x%10;
x/=10;
}
return s;
}
}
-
广度优先遍历bfs +记录
详细代码如下:
class Solution {
public int movingCount(int m, int n, int k) {
// 记忆数组
boolean[][] clew=new boolean[m][n];
int sum=0;
//创建一个队列,保存的是访问到的格子坐标,是个二维数组
Queue<int[]> queue = new LinkedList<>();
//从左上角坐标[0,0]点开始访问,add方法表示把坐标
// 点加入到队列的队尾
queue.add(new int[]{0, 0});
while (queue.size() > 0) {
//这里的poll()函数表示的是移除队列头部元素,因为队列
// 是先进先出,从尾部添加,从头部移除
int[] x = queue.poll();
int i = x[0], j = x[1];
//i >= m || j >= n是边界条件的判断,然后判断当前格子坐标是否满足条件,clew[i][j]判断这个格子是否被访问过
if (i >= m || j >= n || k < get(i)+get(j) || clew[i][j])
continue;
//标注这个格子被访问过
clew[i][j] = true;
sum++;
//把当前格子下边格子的坐标加入到队列中
queue.add(new int[]{i + 1, j});
//把当前格子右边格子的坐标加入到队列中
queue.add(new int[]{i, j + 1});
}
return sum;
}
private int get(int x){
int s=0;
while(x>0){
s=s+x%10;
x/=10;
}
return s;
}
}