迷宫问题

通过深度优先搜索(DFS)方法实现。

迷宫问题一
一天蒜头君掉进了一个迷宫里面,蒜头君想逃出去,可怜的蒜头君连迷宫是否有能逃出去的路都不知道。

看在蒜头君这么可怜的份上,就请聪明的你告诉蒜头君是否有可以逃出去的路。

输入格式
第一行输入两个整数 nn 和 mm,表示这是一个 n \times mn×m 的迷宫。 接下来的输入一个 nn 行 mm 列的迷宫。其中 'S' 表示蒜头君的位置,'*'表示墙,蒜头君无法通过,'.'表示路,蒜头君可以通过'.'移动,'T'表示迷宫的出口(蒜头君每次只能移动到四个与他相邻的位置——上,下,左,右)。 输出格式
输出一个字符串,如果蒜头君可以逃出迷宫输出"yes",否则输出"no"。 数据范围
1 \le n, m \le 101≤n,m≤10。 输出时每行末尾的多余空格,不影响答案正确性 样例输入1复制
3 4
S**.
..*.
***T
样例输出1复制
no
样例输入2复制
3 4
S**.
....
***T
样例输出2复制
yes

题解

我们读入所有数据,然后获得起点S的坐标。然后深度优先遍历,在迷宫问题中进入DFS后,要先判断是否到中点,在判断是否是障碍物,然后标记该点访问过了。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm> using namespace std;
const int N=15;
int n,m;
char g[N][N];
int dx[4]={-1,0,1,0},dy[4]={0,1,0,-1};
bool st[N][N];
bool dfs(int x,int y){
if(g[x][y]=='T'){
return true;
}
if(g[x][y]=='*') return false;
st[x][y]=true;
for(int i=0;i<4;i++){
int a=x+dx[i],b=y+dy[i];
if(a>n||a<=0||b<=0||b>m)continue;
if(st[a][b])continue;
if(dfs(a,b)){
return true;
}
}
return false;
}
int main(){
cin>>n>>m;
int x,y;
for(int i=1;i<=n;i++){
for(int j=1;j<=m;j++){
cin>>g[i][j];
if(g[i][j]=='S'){
x=i;
y=j;
}
}
}
if(dfs(x,y)){
cout<<"yes"<<endl;
}else{
cout<<"no"<<endl;
} return 0;
}
迷宫问题二
蒜头君在你的帮助下终于逃出了迷宫,但是蒜头君并没有沉浸于喜悦之中,而是很快的又陷入了思考,从这个迷宫逃出的最少步数是多少呢?

输入格式
第一行输入两个整数 nn 和 mm,表示这是一个 n \times mn×m 的迷宫。 接下来的输入一个 nn 行 mm 列的迷宫。其中 'S' 表示蒜头君的位置,'*'表示墙,蒜头君无法通过,'.'表示路,蒜头君可以通过'.'移动,'T'表示迷宫的出口(蒜头君每次只能移动到四个与他相邻的位置——上,下,左,右)。 输出格式
输出整数,表示蒜头君逃出迷宫的最少步数,如果蒜头君无法逃出迷宫输出 -1−1。 数据范围
1 \le n, m \le 101≤n,m≤10。 输出时每行末尾的多余空格,不影响答案正确性 样例输入1复制
3 4
S**.
..*.
***T
样例输出1复制
-1
样例输入2复制
3 4
S**.
....
***T
样例输出2复制
5

题解

本题要求判断是否可以到达并且要计算出最短路径,其实用宽度优先搜索更为合适,因为宽度优先搜索第一次到达目的地就是最短路径,但是我们使用深度优先也可以实现,我们定义一个最短量来储存最短的路径,当每一次到达目的点就比较一下与最短路的大小,交换最短路径长度,因此我们要遍历所有的可行路径,所以就要回溯访问状态,所以在一个遍历后就要复原,将一个点置为未访问,额额额,在 这道题中,我开始忘了读入n和m所以出现了segment段错误,还检查了好久没查到。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm> using namespace std;
const int N=15;
char g[N][N];
bool st[N][N];
int Min=99999;
int m,n;
int dx[4]={-1,0,1,0},dy[4]={0,1,0,-1};
void dfs(int x,int y,int stmp){
if(stmp>Min) return ;
if(g[x][y]=='T'){
Min=min(Min,stmp);
return;
}
st[x][y]=true;
if(g[x][y]=='*') return ;
for(int i=0;i<4;i++){
int a=x+dx[i],b=y+dy[i];
if(a>n||a<=0||b>m||b<=0) continue;
if(st[a][b]) continue;
if(g[a][b]=='*') continue;
dfs(a,b,stmp+1);
st[a][b]=false; }
}
int main(){
cin>>n>>m;
int a,b;
for(int i=1;i<=n;i++){
for(int j=1;j<=m;j++){
cin>>g[i][j];
if(g[i][j]=='S'){
a=i,b=j;
}
}
}
dfs(a,b,0);
if(Min==99999){
cout<<-1<<endl;
}else{
cout<<Min<<endl;
}
return 0;
}
迷宫问题三
经过思考蒜头君终于解决了怎么计算一个迷宫的最短路问题,于是蒜头君找到一个新的迷宫图,来验证自己是否真的会计算一个迷宫的最短路。

为了检验自己计算的是否正确,蒜头君特邀你一起来计算。

输入格式
第一行输入两个整数 nn 和 mm,表示这是一个 n \times mn×m 的迷宫。 接下来的输入一个 nn 行 mm 列的迷宫。其中'@'表示蒜头君的位置,'#'表示墙,蒜头君无法通过,'.'表示路,蒜头君可以通过'.'移动,所有在迷宫最外围的'.'都表示迷宫的出口(蒜头君每次只能移动到四个与他相邻的位置——上,下,左,右)。 输出格式
输出整数,表示蒜头君逃出迷宫的最少步数,如果蒜头君无法逃出迷宫输出 -1−1。 数据范围
1 \le n,m \le 151≤n,m≤15。 输出时每行末尾的多余空格,不影响答案正确性 样例输入1复制
9 13
#############
#@..........#
#####.#.#.#.#
#...........#
#.#.#.#.#.#.#
#.#.......#.#
#.#.#.#.#.#.#
#...........#
#####.#######
样例输出1复制
11
样例输入2复制
4 6
#.####
#.#.##
#...@#
######
样例输出2复制
5

题解

该迷宫问题与第二个迷宫问题类似,我们也要求出最短路径,所以一样要使用minn记录短的路径。

但是这个题要注意到达的条件,和第二个迷宫终点判断不一样,这个题要观察迷宫的构造,判断终止条件。所以这道题尽量从1开始存储迷宫图。

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm> using namespace std;
const int N=20;
int n,m;
int dx[4]={-1,0,1,0},dy[4]={0,1,0,-1};
char g[N][N];
bool st[N][N];
int minn=99999;
void dfs(int x,int y,int stmp){
if(stmp>minn)return ;
if(x==0||y==0||x==n+1||y==m+1){
minn=min(minn,stmp);
return ;
}
st[x][y]=true;
for(int i=0;i<4;i++){
int a=x+dx[i],b=y+dy[i];
if(g[a][b]=='#')continue;
if(st[a][b])continue;
dfs(a,b,stmp+1);
st[a][b]=false;
} }
int main(){
cin>>n>>m;
int x,y;
for(int i=1;i<=n;i++){
for(int j=1;j<=m;j++){
cin>>g[i][j];
if(g[i][j]=='@'){
x=i;y=j;
}
}
}
dfs(x,y,0);
if(minn==99999){
cout<<-1<<endl;
}else{
cout<<minn-1<<endl;
}
return 0;
}

好了,dfs递归就先写到这里,之后图论的时候我们在聊。

递推

算法基础③--DFS解决迷宫问题入门的更多相关文章

  1. BFS 、DFS 解决迷宫入门问题

    问题 B: 逃离迷宫二 时间限制: 1 Sec  内存限制: 128 MB提交: 12  解决: 5[提交][状态][讨论版] 题目描述 王子深爱着公主.但是一天,公主被妖怪抓走了,并且被关到了迷宫. ...

  2. 算法基础-dfs

    最近在学dfs(深度优先搜索),dfs与树的遍历差不多,就是先从一个点开始一直搜索,直到走不动为止.现在推荐一个简单的dfs题, 百炼的2815, ########################## ...

  3. 有关dfs、bfs解决迷宫问题的个人见解

    可以使用BFS或者DFS方法解决的迷宫问题! 题目如下: kotori在一个n*m迷宫里,迷宫的最外层被岩浆淹没,无法涉足,迷宫内有k个出口.kotori只能上下左右四个方向移动.她想知道有多少出口是 ...

  4. 算法基础:BFS和DFS的直观解释

    算法基础:BFS和DFS的直观解释 https://cuijiahua.com/blog/2018/01/alogrithm_10.html 一.前言 我们首次接触 BFS 和 DFS 时,应该是在数 ...

  5. 用深度优先搜索(DFS)解决多数图论问题

    前言 本文大概是作者对图论大部分内容的分析和总结吧,\(\text{OI}\)和语文能力有限,且部分说明和推导可能有错误和不足,希望能指出. 创作本文是为了提供彼此学习交流的机会,也算是作者在忙碌的中 ...

  6. 《Java基础复习》—常识与入门

    突然发现自己Java基础的底子不到位,复习! 所记知识会发布在CSDN与博客网站jirath.cn <Java基础复习>-常识与入门 一.Java语言的知识体系图 分为三部分 编程语言核心 ...

  7. 2020牛客寒假算法基础集训营1 J题可以回顾回顾

    2020牛客寒假算法基础集训营1 这套题整体来说还是很简单的. A.honoka和格点三角形 这个题目不是很难,不过要考虑周全,面积是1,那么底边的长度可以是1也可以是2, 注意底边1和2会有重复的, ...

  8. DFS 深搜专题 入门典例 -- 凌宸1642

    DFS 深搜专题 入门典例 -- 凌宸1642 深度优先搜索 是一种 枚举所有完整路径以遍历所有情况的搜索方法 ,使用 递归 可以很好的实现 深度优先搜索. 1 最大价值 题目描述 ​ 有 n 件物品 ...

  9. 解读Raft(一 算法基础)

    最近工作中讨论到了Raft协议相关的一些问题,正好之前读过多次Raft协议的那paper,所以趁着讨论做一次总结整理. 我会将Raft协议拆成四个部分去总结: 算法基础 选举和日志复制 安全性 节点变 ...

随机推荐

  1. vim设置自动添加头部注释

    #自己改了改vim开头文件,如下图# 友友们可以直接修改·SetTitle() if v:lang =~ "utf8$" || v:lang =~ "UTF-8$&quo ...

  2. 内网代理工具--EarthWorm

    一.简介 EarthWorm是内网穿透的神器,拥有三项功能正向代理,反向代理,端口转发. 为实现这些功能,EarthWorm建立了六大功能模块.分别是ssocksd , rcsocks , rssoc ...

  3. 74CMS 3.0 任意文件删除漏洞

    一. 启动环境 1.双击运行桌面phpstudy.exe软件 2.点击启动按钮,启动服务器环境 二.代码审计 1.双击启动桌面Seay源代码审计系统软件 2.因为74CMS3.0源代码编辑使用GBK编 ...

  4. 浅析Redis基础数据结构

    Redis是一种内存数据库,所以可以很方便的直接基于内存中的数据结构,对外提供众多的接口,而这些接口实际上就是对不同的数据结构进行操作的算法,首先redis本身是一种key-value的数据库,对于v ...

  5. CSS入门笔记

    CSS @author:伏月廿柒 Cascading Style Sheet 层叠级联样式表 CSS:表现(美化) 字体,颜色,边距,高度,宽度,背景图片,网页定位,网页浮动-- CSS发展史 CSS ...

  6. mysql join 底层原理

    你知道 Sql 中 left join 的底层原理吗? 2019-09-10阅读 7130 https://cloud.tencent.com/developer/column/2367   01.前 ...

  7. Captcha生成验证码,docker部署时问题

    https://blog.csdn.net/huofuman960209/article/details/100738712 Dockerfile FROM openjdk:8-jdk-alpine ...

  8. Spring Boot 需要独立的容器运行吗?

    可以不需要,内置了 Tomcat/ Jetty 等容器.

  9. 为什么要配置JDK环境变量?

    1. PATH环境变量.作用是指定命令搜索路径,在shell下面执行命令时,它会到PATH变量所指定的路径中查找看是否能找到相应的命令程序.我们需要把 jdk安装目录下的bin目录增加到现有的PATH ...

  10. 什么是 Aspect?

    aspect 由 pointcount 和 advice 组成, 它既包含了横切逻辑的定义, 也包 括了连接点的定义. Spring AOP 就是负责实施切面的框架, 它将切面所定义的横 切逻辑编织到 ...