package com.heu.wsq.leetcode.inoffer;
/**
* 剑指 Offer 13. 机器人的运动范围
* @author wsq
* @date 2021/4/13
* 地上有一个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
*
* 链接:https://leetcode-cn.com/problems/ji-qi-ren-de-yun-dong-fan-wei-lcof
*/
public class Offer13 {
/**
* 节点移动方向
*/
private static final int[][] direction = {{0, 1}, {1, 0}, {0, -1}, {-1, 0}};
private static int ans;
private int m;
private int n;
private int k;
public int movingCount(int m, int n, int k) {
ans = 0;
if(m == 0 && n == 0){
return ans;
}
this.m = m;
this.n = n;
this.k = k;
boolean[][] visited = new boolean[m][n];
dfs(0, 0, visited);
return ans;
}
private void dfs(int row, int col, boolean[][] visited){
// System.out.println(row + "," + col);
if(row < 0 || row >= m || col < 0 || col >= n || rowColSum(row, col) > this.k
|| visited[row][col]){
return;
}
ans++;
visited[row][col] = true;
// 再从该点将上下左右四个方向移动
for(int[] d: direction){
int x = row + d[0];
int y = col + d[1];
dfs(x, y, visited);
}
}
/**
* 求横纵坐标的位之和
* @param row
* @param col
* @return
*/
private int rowColSum(int row, int col){
int sum = 0;
while(row > 0){
int tmp = row % 10;
row /= 10;
sum += tmp;
}
while(col > 0){
int tmp = col % 10;
col /= 10;
sum += tmp;
}
return sum;
}
}
剑指 Offer 13. 机器人的运动范围(回溯算法)
最新推荐文章于 2025-04-13 18:04:40 发布