题目
题目链接
地上有一个m行n列的方格,从坐标 [0,0] 到坐标 [m-1,n-1] 。一个机器人从坐标 [0, 0] 的格子开始移动,它每次可以向左、右、上、下移动一格(不能移动到方格外),也不能进入行坐标和列坐标的数位之和大于k的格子。例如,当k为18时,机器人能够进入方格 [35, 37] ,因为3+5+3+7=18。但它不能进入方格 [35, 38],因为3+5+3+8=19。请问该机器人能够到达多少个格子?
示例 1:
输入:m = 2, n = 3, k = 1
输出:3
示例 2:
输入:m = 3, n = 1, k = 0
输出:1
提示:
1 <= n,m <= 100
0 <= k <= 20
解题思路
简单递归,题目规定从坐标【0,0】出发,可以上下左右的移动一格,但是必须保证横坐标和纵坐标的树位之和不能大于k。
举例说明 流程如下:
输入:m = 2, n = 3, k = 1
2行3列的二维数组 * 代表格子 o代表机器人走过的格子
【
*,*,*
*,*,*
】
当前机器人所在的位置:【0,0】
【
o,*,*
*,*,*
】
数位和 0+0<1 满足条件 可以进行下一次移动(上下左右任意方向)
向左向上肯定不行 因为超出边界 只能向右或者向下
先向右移动一格
【
o,o,*
*,*,*
】
当前机器人所在位置【0,1】
数位和 0+1<=1 满足条件 可以进行下一次移动(上下左右任意方向)
向右移动一格(此步是说明不满足条件)
【
o,o,o
*,*,*
】
当前机器人所在位置【0,2】
数位和 0+2>1 不满足条件 所以此步无效, (递归回退)只能由【0,1】的位置向下运动
因为【0,0】走过,【0,2】不满足条件
(此步是说明不满足条件)
【
o,o,*
*,o,*
】
当前机器人所在位置【1,1】
数位和 1+1>1 不满足条件 所以此步无效 , (递归回退)只能由【0,0】的位置向下运动
因为【0,2】不满足条件 【1,1】不满足条件
【
o,o,*
o,*,*
】
当前机器人所在位置【1,0】
在进行上下左右都不满足所以停止。
满足条件的格子共有3个
实现:
定义一个visited数组记录当前位置是否走过。
定义一个二维数组matrix记录所有的格子
i,j表示当前的位置坐标
sums方法求数位和
递归终止条件:当超出边界或者该格子访问过或者数位和不满足条件时。
需要注意的是:格子可以多次走过,但是走过了的就不能在算新格子加1,所以我这么设计
代码
class Solution {
private int sum = 0;
public int movingCount(int m, int n, int k) {
int[][] matrix = new int[m][n];
int[][] visited = new int[matrix.length][matrix[0].length];
moving(matrix, visited, 0, 0, k);
return sum;
}
public void moving(int[][] matrix, int[][] visited, int i, int j, int k) {
//当超出边界或者该格子访问过或者数位和不满足条件时。 递归终止
if (i < 0 || j < 0 || i >= matrix.length || j >= matrix[0].length || visited[i][j] == 1 || sums(i) + sums(j) > k) {
return;
}
//满足所有条件 机器人能到达的格子数加1
if (visited[i][j] == 0 && sums(i) + sums(j) <= k) {
sum += 1;
}
visited[i][j] = 1;//记录标记
moving(matrix, visited, i, j - 1, k);//左
moving(matrix, visited, i, j + 1, k);//右
moving(matrix, visited, i - 1, j, k);//上
moving(matrix, visited, i + 1, j, k);//下
}
/**
* 求数位和
* @param x
* @return
*/
private int sums(int x) {
int s = 0;
while (x != 0) {
s += x % 10;
x = x / 10;
}
return s;
}
}