[BFS]洪水

2024-01-30 06:32
文章标签 bfs 洪水

本文主要是介绍[BFS]洪水,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

题目描述

一天, 一个画家在森林里写生,突然爆发了山洪,他需要尽快返回住所中,那里是安
全的。
森林的地图由R行C列组成,空白区域用点“.”表示,洪水的区域用“*”表示,而
岩石用“X”表示,另画家的住所用“D”表示,画家用“S”表示。
有以下几点需要说明:
1、 每一分钟画家能向四个方向移动一格(上、下、左、右)
2、 每一分钟洪水能蔓延到四个方向的相邻格子(空白区域)
3、 洪水和画家都不能通过岩石区域
4、 画家不能通过洪水区域(同时也不行,即画家不能移到某个格子,该格子在画家达到的同时被洪水蔓延到了,这也是不允许的)
5、 洪水蔓不到画家的住所。
给你森林的地图,编写程序输出最少需要花费多长时间才能从开始的位置赶回家中。

Input

输入第一行包含两个整数R和C(R,C<=50)。
接下来R行每行包含C个字符(“.”、“*”、“X”、“D”或“S”)。地图保证只有一个“D”和一个“S”。

Output

输出画家最快安全到达住所所需的时间,如果画家不可能安全回家则输出“KAKTUS”。

Sample Input

输入1:
3 3
D.*

.S.

输入2:
3 3
D.*

..S

输入3:
3 6
D…*.
.X.X..
….S.

分析

这题其实很简单,洪水单独一个队列bfs,画家一个队列bfs,然后判断画家到某格时深度是否比洪水深,深就不能过了,然后每个点只用走一次,因为宽度优先搜索先搜到的深度一定最小

#include <iostream>
#include <cstdio>
#define rep(i,a,b) for (i=a;i<=b;i++)
using namespace std;
int r,c,k;
int b[51][51];
int sx,sy,ex,ey;
int q[2501][2];
int dep[51][51][2];
int dx[4]={0,0,1,-1},dy[4]={1,-1,0,0};
bool judg(int x,int y)
{return x>=1&&x<=r&&y>=1&&y<=c&&b[x][y]==0;
}
bool judge(int x,int y,int z)
{return x>=1&&x<=r&&y>=1&&y<=c&&b[x][y]<=0&&z<dep[x][y][0];
}
void bfs1()
{int h=0,i,j;bool w[51][51];rep(i,1,50) rep(j,1,50) w[i][j]=0;do{h++;rep(i,0,3)if (judg(q[h][0]+dx[i],q[h][1]+dy[i])&&!w[q[h][0]+dx[i]][q[h][1]+dy[i]]){k++;q[k][0]=q[h][0]+dx[i];q[k][1]=q[h][1]+dy[i];w[q[k][0]][q[k][1]]=1;dep[q[k][0]][q[k][1]][0]=dep[q[h][0]][q[h][1]][0]+1;}}while (h<k);
}
void bfs2()
{int h=0,t=1,i,j,state[2501][2];bool w[51][51];rep(i,1,50) rep(j,1,50) w[i][j]=0;state[1][0]=sx;state[1][1]=sy;w[sx][sy]=1;do{h++;rep(i,0,3)if (judge(state[h][0]+dx[i],state[h][1]+dy[i],dep[state[h][0]][state[h][1]][1]+1)&&!w[state[h][0]+dx[i]][state[h][1]+dy[i]]){t++;state[t][0]=state[h][0]+dx[i];state[t][1]=state[h][1]+dy[i];w[state[t][0]][state[t][1]]=1;dep[state[t][0]][state[t][1]][1]=dep[state[h][0]][state[h][1]][1]+1;}}while (h<t);
}
void init()
{int i,j;char p;scanf("%d%d",&r,&c);rep(i,1,r)rep(j,1,c)dep[i][j][0]=2147483647;rep(i,1,r)rep(j,1,c){do{scanf("%c",&p);}while (p!='*'&&p!='.'&&p!='X'&&p!='S'&&p!='D');switch (p){case 'S':{sx=i;sy=j;break;}case 'X':{b[i][j]=1;break;}case '*':{k++;q[k][0]=i;q[k][1]=j;dep[i][j][0]=0;b[i][j]=2;break;}case 'D':{ex=i;ey=j;b[i][j]=-1;break;}default:{break;}}}
}
void doit()
{if (k!=0) bfs1();bfs2();if (dep[ex][ey][1]!=0) printf("%d",dep[ex][ey][1]);else printf("KAKTUS");
}
int main()
{init();doit();
}

这篇关于[BFS]洪水的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/659365

相关文章

hdu1254(嵌套bfs,两次bfs)

/*第一次做这种题感觉很有压力,思路还是有点混乱,总是wa,改了好多次才ac的思路:把箱子的移动当做第一层bfs,队列节点要用到当前箱子坐标(x,y),走的次数step,当前人的weizhi(man_x,man_y),要判断人能否将箱子推到某点时要嵌套第二层bfs(人的移动);代码如下:

poj 2195 bfs+有流量限制的最小费用流

题意: 给一张n * m(100 * 100)的图,图中” . " 代表空地, “ M ” 代表人, “ H ” 代表家。 现在,要你安排每个人从他所在的地方移动到家里,每移动一格的消耗是1,求最小的消耗。 人可以移动到家的那一格但是不进去。 解析: 先用bfs搞出每个M与每个H的距离。 然后就是网络流的建图过程了,先抽象出源点s和汇点t。 令源点与每个人相连,容量为1,费用为

POJ 3057 最大二分匹配+bfs + 二分

SampleInput35 5XXDXXX...XD...XX...DXXXXX5 12XXXXXXXXXXXXX..........DX.XXXXXXXXXXX..........XXXXXXXXXXXXX5 5XDXXXX.X.DXX.XXD.X.XXXXDXSampleOutput321impossible

深度优先(DFS)和广度优先(BFS)——算法

深度优先 深度优先搜索算法(英语:Depth-First-Search,DFS)是一种用于遍历或搜索树或图的算法。 沿着树的深度遍历树的节点,尽可能深的搜索树的分支,当节点v的所在边都己被探寻过,搜索将回溯到发现节点v的那条边的起始节点。这一过程一直进行到已发现从源节点可达的所有节点为止。如果还存在未被发现的节点,则选择其中一个作为源节点并重复以上过程,整个进程反复进行直到所有节点都被访

双头BFS

牛客月赛100 D题,过了80%数据,调了一下午。。。烦死了。。。 还是没调试出来,别人的代码用5维的距离的更新有滞后性,要在遍历之前要去重。。。 #include<bits/stdc++.h>using namespace std;const int N=2e3+10;char g[N][N];int dis[N][N],d1[N][N];int n,m,sx,sy;int dx

Knight Moves -uva 简单的BFS遍历

昨天刚学了BFS的遍历,在uva上找了个题敲了出来,感觉还不错,最近敲代码挺有手感的,希望这种状态保持下去 #include<iostream>#include<stdio.h>#include<stdlib.h>#include<string.h>#define MAX_SIZE 10 + 5#define LEN 100 + 10using namespace std;in

【CF】D. Arthur and Walls(BFS + 贪心)

D题 解题思路就是每次检查2X2的方格里是否只有一个‘*’,如果有的话这个*就需要变成‘.’,利用BFS进行遍历,入队的要求是这个点为. 一开始将所有的'.'全部加入队列,如果碰到一个'*'变成'.'就入队,判断的时候从4个方向就行判断 题目链接:http://codeforces.com/contest/525/problem/D #include<cstdio>#include<

hdu2717(裸bfs广搜)

Catch That Cow Time Limit: 5000/2000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 7304 Accepted Submission(s): 2308 题目链接: http://acm.hdu.edu.cn/showproblem.

Codeforces#295(Div.2)A、B(模拟+BFS)

解题报告链接:点击打开链接 C. 题目链接:点击打开链接 解题思路: 对于给定的字符串,取出现次数最多的字母(可以同时有多个)。由这些字母组成长度为n的字符串,求有多少种组合。最后用数学知识即可。 完整代码: #include <algorithm>#include <iostream>#include <cstring>#include <climits>

java常用算法之字梯(广度优先搜索bfs)

<span style="font-family: 'microsoft yahei', simhei, arial, sans-serif; font-size: 16px;">给定2个单词(start</span><span style="font-family: 'microsoft yahei', simhei, arial, sans-serif; font-size: 16px;">和