小虫子逃迷宫

今天的题目是一道小虫子逃迷宫的题

我们先来读读题。

----------
由于新冠肺炎疫情的爆发,小明养在宿舍的小昆虫已经很久很久都没有人管了。小昆虫已经饿的不行了,
必须出来找东西吃,可是出来之后需要走出一个迷宫。小昆虫每次可以朝上、下、左、右四个方向之一走步,
且只要走出任意一条边界线即可逃出迷宫。这只小昆虫曾感染过X星的一种奇异病毒,目前还没有发现任何副作用,
但是却拥有了一项特异功能—破坏障碍物。

假设小昆虫在一个 N*M 的迷宫中,① "@"代表小昆虫的初始位置,② "."代表可以通过的空地,
③"*"代表可以破坏的障碍物,④"#代表不可破坏的障碍物。请问小昆虫最少需要使用多少次特异功能才可以逃出迷宫?
 
 输入描述

 多组数据,第1行有1个正整数T,表示有T组数据。 (T<=100)
 对于每组数据,第1行有两个整数N和M。(1<=N, M<=1000)
 接着N行,每行有一个长度为M的字符串,表示N*M的迷宫。
 输出描述

 Plain  Text
   输出一个整数,表示使用特异功能的最少次数。如果小昆虫不能走出迷宫,则输出-1.
   --------》
   样例输入 :
   3
   3 3
   ###
   #@*
   ***
   3 4
   ####
   #@.*
   **.*
   3 3
   .#.
   #@#
   .#.
   --------》
   样例输出 :
   
   1
   0
   -1

读完题,当时没感觉到啥,但一看到输入输出,咦,又是一个二维的字符数组,根据题意可以得出本题的意思是在二维数组中判断从@开始,到跳出二维数组,有多少种方法,然后从这些方法中找出使用 “ . ” 最少的那个呀,所以这个题我们还是需要用深度优先搜索来做。

老规矩,判断完是使用搜索来做之后,我们就来找递归三要素。

一,函数设计

遇到在二维数组中找符合条件的个数的问题,就先把 行和列 写上,然后在给一个变量记录每一种方法中,使用特异功能的次数 。

		 public void dfs(int i, int j, int count)

二,终止条件

跳出二维数组就是需要终止啦。

	if (i < 0 || j < 0 || i >= row || j >= col) {
            res = Math.min(res, count); // 求出每一次跳出循环时,当前最少的 ‘.’的个数
            return;
        }

三,递归方向

在二维数组中找东西,方向有且只有上下左右四个方向,难不成还要斜着找嘛(有的变态题可能还真有!)

        dfs(i + 1, j, count);
        dfs(i, j + 1, count);
        dfs(i - 1, j, count);
        dfs(i, j - 1, count);

代码贴出来:

在这里插入代码片

    public int getInsect(char[][] chars , int N , int M , int startI , int startJ) {
        N = row;
        M = col;
        this.visited = new boolean[N][M] ;
        this.res = Integer.MAX_VALUE ;
        dfs(startI,startJ,0);
        return res == Integer.MAX_VALUE ? -1 : res ;
    }
    
    char[][] c ;
    int row , col ;
    int res ;
    boolean[][] visited ;
    
    public void dfs(int i , int j , int count) {
        if (i<0||j<0||i>row||j>=col) {
            // 将当前的跳出是.的个数与上一个相比,这样可以得出最后得到的值是最少的
            res = Math.min(res,count) ; 
            return;
        }
        if (visited[i][j] = true) return; // 染色,保证每一次走过的路都不会再走
        visited[i][j] = true ;
        if (c[i][j] == '#') return;
        if (c[i][j] == '*') count++ ;
        dfs(i+1,j,count);//右
        dfs(i-1,j,count);//左
        dfs(i,j+1,count);//上
        dfs(i,j-1,count);//下
        visited[i][j] = false; //回溯操作 清除刚才的记录 防止下一次函数被调用时结果收到上一条影响
    }

写完了 ,我们来写个main方法来测试下。

在这里插入代码片
public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int T = scanner.nextInt();
        while (T > 0) { // 表示T组数据
            int N, M, starti = 0, startj = 0;
            N = scanner.nextInt(); // M行
            M = scanner.nextInt(); // N列
            scanner.nextLine();     //这个表示可以读取空格 表示我们要换行输入啦~
            char[][] map = new char[N][M];
            for (int i = 0; i < N; i++) {
                char[] tmp = scanner.nextLine().toCharArray(); //每一行都是一个一维数组
                for (int j = 0; j < M; j++) {
                    map[i][j] = tmp[j];
                    if (tmp[j] == '@') { //找到起始点 然后递归哦
                        starti = i;
                        startj = j;
                    }
                }
            }
            System.out.println(new insect().solution(map, N, M, starti, startj));
            T--;
        }
    }

测试结果如下:
在这里插入图片描述
搞定!

2020年11月24日18:37:55

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
【优质项目推荐】 1、项目代码均经过严格本地测试,运行OK,确保功能稳定后才上传平台。可放心下载并立即投入使用,若遇到任何使用问题,随时欢迎私信反馈与沟通,博主会第一时间回复。 2、项目适用于计算机相关专业(如计科、信息安全、数据科学、人工智能、通信、物联网、自动化、电子信息等)的在校学生、专业教师,或企业员工,小白入门等都适用。 3、该项目不仅具有很高的学习借鉴价值,对于初学者来说,也是入门进阶的绝佳选择;当然也可以直接用于 毕设、课设、期末大作业或项目初期立项演示等。 3、开放创新:如果您有一定基础,且热爱探索钻研,可以在此代码基础上二次开发,进行修改、扩展,创造出属于自己的独特应用。 欢迎下载使用优质资源!欢迎借鉴使用,并欢迎学习交流,共同探索编程的无穷魅力! 基于业务逻辑生成特征变量python实现源码+数据集+超详细注释.zip基于业务逻辑生成特征变量python实现源码+数据集+超详细注释.zip基于业务逻辑生成特征变量python实现源码+数据集+超详细注释.zip基于业务逻辑生成特征变量python实现源码+数据集+超详细注释.zip基于业务逻辑生成特征变量python实现源码+数据集+超详细注释.zip基于业务逻辑生成特征变量python实现源码+数据集+超详细注释.zip基于业务逻辑生成特征变量python实现源码+数据集+超详细注释.zip 基于业务逻辑生成特征变量python实现源码+数据集+超详细注释.zip 基于业务逻辑生成特征变量python实现源码+数据集+超详细注释.zip

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值