剑指66机器人的运动范围

public class JZ6601 {

    private final static int[][] next={{0,1},{0,-1},{1,0},{-1,0}};
    private int cnt=0;
    private int rows;
    private int cols;
    private int threshold;
    private int[][] digitSum;

    public int movingCount(int threshold, int rows, int cols) {

        this.rows=rows;
        this.cols=cols;
        this.threshold=threshold;
        initDigitSum();
        boolean[][] marked=new boolean[rows][cols];
        dfs(marked,0,0);
        return cnt;
    }

    private void dfs(boolean[][] marked,int r,int c){
        if(r<0||r>=rows||c<0||c>=cols||marked[r][c])
            return;
        marked[r][c]=true;
        if(this.digitSum[r][c]>this.threshold){
            return;
        }
        cnt++;
        for(int[] n:next){
            dfs(marked,r+n[0],r+n[1]);
        }
    }

    public void initDigitSum(){

        int[] digitSumOne=new int[Math.max(rows,cols)];
        for(int i=0;i<digitSumOne.length;i++){
            int n=i;
            while(n>0){
                digitSumOne[i]+=n%10;
                n/=10;
            }
        }

        this.digitSum=new int[rows][cols];
        for(int i=0;i<rows;i++){
            for(int j=0;j<cols;j++){
                digitSum[i][j]=digitSumOne[i]+digitSumOne[j];
            }
        }
    }
}

使用深度优先算法(dfs),不断向下递归求解,直到遇到边界条件再进行回溯。

import java.util.*;
public class Solution {
    private  int[][] digitSum;
    private int rows;
    private int cols;
    
    public int movingCount(int threshold, int rows, int cols) {
        boolean[][] marked=new boolean[rows][cols];
        int res=0;
        this.rows=rows;
        this.cols=cols;
        initDigitSum();
        Queue<int[]> queue=new LinkedList<>();
        queue.add(new int[]{0,0});

        while(queue.size()>0){

            int[] temp=queue.poll();
            int i=temp[0],j=temp[1];
            if(i>=rows||j>=cols||threshold<digitSum[i][j]||marked[i][j])
                continue;
            marked[i][j]=true;
            res++;
            //不需要向上向左遍历
            queue.add(new int[]{i+1,j});
            queue.add(new int[]{i,j+1});
        }
        return res;
    }
    
    public void initDigitSum(){

        int[] digitSumOne=new int[Math.max(rows,cols)];
        for(int i=0;i<digitSumOne.length;i++){
            int n=i;
            while(n>0){
                digitSumOne[i]+=n%10;
                n/=10;
            }
        }

        this.digitSum=new int[rows][cols];
        for(int i=0;i<rows;i++){
            for(int j=0;j<cols;j++){
                digitSum[i][j]=digitSumOne[i]+digitSumOne[j];
            }
        }
    }
}

使用广度优先算法(BFS),用队列保存遍历相邻格子的坐标,根据队列先进先出的特点,优先遍历了相邻格子;用矩阵digitSum来保存坐标数字相加的值。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值