题目描述
本题重点有三个:
·不超出方格范围(坐标大于0,小于等于rols(cols))
·不重复访问格子,这里使用visited数组来判断
·坐标值每位之和小于k
时间复杂度
最大可能的遍历次数:
在最坏的情况下,机器人需要遍历整个网格的每个格子一次。假设网格的大小为 m × n(rows 为 m,cols 为 n),那么最多有 m × n 个格子。
遍历的时间复杂度:
每次递归调用都会检查当前格子的四个邻居(上、下、左、右),因此每个格子的访问可能会导致最多4次递归调用。不过,借助visited数组的帮助,每个格子只会被访问一次。因此,总的时间复杂度与遍历的格子数量成线性关系。
综合时间复杂度:
由于每个格子最多访问一次,时间复杂度为 O(mn),其中 m 是网格的行数,n 是网格的列数。
C++ 代码
class Solution {
public:
int movingCount(int threshold, int rows, int cols) {
vector<vector<bool>> visited(rows, vector<bool>(cols, false));
//用vector容器定义二维数组visited,行rows,宽cols视visited为一个大数组,包含了 rows 个长度为 cols 的小数组,值初始化为false(即未被访问)
return recursion(0, 0, threshold, rows, cols, visited);
}
private:
int recursion(int x, int y, int threshold, int rows, int cols, vector<vector<bool>>& visited) {
if (x < 0 || x >= rows || y < 0 || y >= cols || visited[x][y] || locsum(x) + locsum(y) > threshold) {
return 0;
//如果不满足:1、在方格范围内;2、未被访问;3、总和小于k;
//则结束该次递归调用,返回值为 0 表示不增加可到达的格子数;
}
visited[x][y] = true;
//满足条件则修改visited数值为true,表示该点已被访问,后续访问不再加一
//用 1(本次递归条件满足,所以加一) 加上 四个方向的递归(从上到下分别是该点的 右,左,上,下)
return 1 + recursion(x + 1, y, threshold, rows, cols, visited)
+ recursion(x - 1, y, threshold, rows, cols, visited)
+ recursion(x, y + 1, threshold, rows, cols, visited)
+ recursion(x, y - 1, threshold, rows, cols, visited);
}
//计算当前位置的各位总和
int locsum(int x) {
int sum = 0;
while (x > 0) {
sum += x % 10;
x /= 10;
}
return sum;
}
};