UVA - 11624

题意:joe在一个迷宫里,迷宫的一些部分着火了,火势会向周围四个方向蔓延,joe可以向四个方向移动。火与人的速度都是1格/1秒,问j能否逃出迷宫,若能输出最小时间。

题解:先考虑模拟火,肯定是bfs(每次把同一时间着火的格子pop出来,再将它们周围的格子的t加一push进去)

    然后考虑怎么模拟人,现在人处在一个会变化的迷宫中。貌似很复杂。

    我们可以考虑t时刻的地图(假设我们bfs人的位置),着火的地方相当于墙壁,已经走过的地方也相当于墙壁(因为不可能回到已经走过的地方,这样要么出不去,要么走了回头路导致时间变长)。队列中存着当前时刻所有人可以到达的位置。考虑我们可以走的位置,除了边界与墙壁,如果我们知到一秒后哪些位置会着火,我们就不会走那些格子(否则就烧死了)。

于是便得到了一个算法,先让火烧一秒,然后人bjs一步,再烧1秒,再走一步。。。。

坑:一开始我先让人走一步,结果完全无法模拟人被火烧到的情况;

用queue的的时候老报错,总是pop空栈(因为没有考虑第一个与同一时刻的最后一个的特殊情况,结果写了一个很混乱的逻辑判断)

正确的方法是:

f v = F.front();
if (v.t == t) {...} else{return;}

  1. #define _CRT_SECURE_NO_WARNINGS
  2. #include<cstdio>
  3. #include<algorithm>
  4. #include<iostream>
  5. #include<string>
  6. #include<vector>
  7. #include<string.h>
  8. #include<queue>
  9. using namespace std;
  10. typedef long long ll;
  11. const int maxn = + ;
  12. //模拟F,深搜J,
  13. //F有多个,J一个
  14. struct f {
  15. int x, y, t;
  16. f(int x = , int y = , int t = ) :x(x), y(y), t(t) {}
  17. };
  18. int dir[][] = { ,, ,-, ,, -, };
  19. char map[maxn][maxn];
  20. int vis[maxn][maxn], fired[maxn][maxn];
  21. queue<f > F, J;
  22. int R, C; int flag = ; int cnt = , square = ; int T = ;
  23. bool check(int x, int y) {
  24. if (map[x][y] == '#' || R < x || x <= || y <= || C < y)return ;
  25. else return ;
  26. }
  27. void spread(int t) {//fire at (x,y) spread.//bfs1层
  28.  
  29. while (!F.empty()) {
  30. f v = F.front();
  31. if (v.t == t) {
  32. map[v.x][v.y] = '#';
  33. F.pop();
  34. for (int i = ; i < ; i++) {
  35. int dx = v.x + dir[i][], dy = v.y + dir[i][];
  36. if (check(dx, dy))continue;
  37. map[dx][dy] = '#';
  38. F.push(f(dx, dy, v.t + ));
  39. }
  40. }
  41. else return;
  42. }
  43. }
  44. void bfs(int t) {//J runs at t
  45. while (!J.empty()) {
  46. f v = J.front();
  47. if (v.t == t) {
  48. J.pop();
  49. for (int i = ; i < ; i++) {
  50. int dx = v.x + dir[i][], dy = v.y + dir[i][];
  51. if (dx <= || dx > R || dy <= || dy > C) { flag = v.t + ; while (!J.empty())J.pop(); return; }
  52. if (map[dx][dy] != '#') {
  53. map[dx][dy] = '#';
  54. J.push(f(dx, dy, v.t + ));
  55. }
  56. }
  57. }
  58. else return;
  59. }
  60. }
  61. int main() {
  62. int t; cin >> t;
  63. while (t--) {
  64. while (!J.empty())J.pop();
  65. while (!F.empty())F.pop();
  66. cin >> R >> C;
  67. for (int i = ; i <= R; i++) {
  68. scanf("%s", map[i] + );
  69. for (int j = ; j <= C; j++)if (map[i][j] == 'F') F.push(f(i, j, )), fired[i][j] = ; else if (map[i][j] == 'J')J.push(f(i, j, )), map[i][j] = '#';
  70. }
  71. flag = -;
  72. T = ;
  73. int tf = , tj = ;
  74. while (!J.empty()) {
  75. spread(T);
  76. bfs(T);
  77. T++;
  78. if (flag > )break;
  79. }
  80.  
  81. if (flag == -)cout << "IMPOSSIBLE" << endl;
  82. else cout << flag << endl;
  83. }
  84. cin >> t;
  85. }

同学的想法是两次bfs,先bfs一次火的,把它抵达各个格子的时间填在一个表里,说明人在这个时间之后就不能走到这里了,把这个判断加到人的bfs里面即可

  1. #define _CRT_SECURE_NO_WARNINGS
  2. #include <iostream>
  3. #include <cstdio>
  4. #include <algorithm>
  5. #include <queue>
  6. #include <vector>
  7. #include <string.h>
  8.  
  9. using namespace std;
  10. char map[][];
  11. int vis[][];
  12. int tf[][];
  13. int n, m, ji, jj, fi, fj;
  14. struct Node {
  15. int i, j;
  16. Node(int i = , int j = ) :i(i), j(j) {}
  17. };
  18. queue<Node>q;
  19. int dir[][] = { { , },{ -, },{ , },{ ,- } };
  20. void bfsf() {
  21. while (!q.empty()) {
  22. Node t = q.front();
  23. q.pop();
  24. for (int k = ; k<; k++) {
  25. int di = t.i + dir[k][];
  26. int dj = t.j + dir[k][];
  27. if (di< || di >= n || dj< || dj >= m || map[di][dj] == '#' || tf[di][dj] != -) continue;
  28. q.push(Node(di, dj));
  29. tf[di][dj] = tf[t.i][t.j] + ;
  30. }
  31. }
  32. }
  33.  
  34. int bfsj(int i, int j) {
  35. queue<Node>que;
  36. que.push(Node(i, j));
  37. vis[i][j] = ;
  38. while (!que.empty()) {
  39. Node t = que.front();
  40. que.pop();
  41. if (t.i == || t.i == n - || t.j == || t.j == m - )
  42. return vis[t.i][t.j] + ;
  43. for (int k = ; k<; k++) {
  44. int di = t.i + dir[k][];
  45. int dj = t.j + dir[k][];
  46. if (di< || di >= n || dj< || dj >= m || map[di][dj] == '#' || (vis[di][dj] != - || vis[t.i][t.j] + >= tf[di][dj]&&tf[di][dj]>)) continue;
  47. que.push(Node(di, dj));
  48. vis[di][dj] = vis[t.i][t.j] + ;
  49. }
  50. }
  51. return -;
  52. }
  53. int main() {
  54. int t;
  55. scanf("%d", &t);
  56. while (t--) {
  57. memset(tf, -, sizeof(tf));
  58. scanf("%d%d", &n, &m);
  59. for (int i = ; i<n; i++) {
  60. scanf("%s", map[i]);
  61. for (int j = ; j<m; j++) {
  62. if (map[i][j] == 'J') ji = i, jj = j;
  63. if (map[i][j] == 'F') q.push(Node(i, j)), tf[i][j] = ;
  64. }
  65. }
  66. bfsf();
  67. /*for (int i = 0; i < n; i++) {
  68. for (int j = 0; j <= m; j++) cout << tf[i][j] << ' '; cout << endl;
  69. }*/
  70.  
  71. memset(vis, -, sizeof(vis));
  72. int ans = bfsj(ji, jj);
  73. if (ans == -) printf("IMPOSSIBLE\n");
  74. else printf("%d\n", ans);
  75.  
  76. }
  77. return ;
  78. }

UVA - 11624 Fire! bfs 地图与人一步一步先后搜/搜一次打表好了再搜一次的更多相关文章

  1. UVA 11624 Fire! (bfs)

    算法指南白书 分别求一次人和火到达各个点的最短时间 #include<cstdio> #include<cstring> #include<queue> #incl ...

  2. UVA 11624 Fire! bfs 难度:0

    http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&p ...

  3. UVA 11624 Fire! BFS搜索

    题意:就是问你能不能在火烧到你之前,走出一个矩形区域,如果有,求出最短的时间 分析:两遍BFS,然后比较边界 #include<cstdio> #include<algorithm& ...

  4. BFS(两点搜索) UVA 11624 Fire!

    题目传送门 /* BFS:首先对火搜索,求出火蔓延到某点的时间,再对J搜索,如果走到的地方火已经烧到了就不入队,直到走出边界. */ /******************************** ...

  5. UVa 11624 Fire!(着火了!)

    UVa 11624 - Fire!(着火了!) Time limit: 1.000 seconds Description - 题目描述 Joe works in a maze. Unfortunat ...

  6. E - Fire! UVA - 11624(bfs + 记录火到达某个位置所需要的最小时间)

    E - Fire! UVA - 11624 题目描述 乔在迷宫中工作.不幸的是,迷宫的一部分着火了,迷宫的主人没有制定火灾的逃跑计划.请帮助乔逃离迷宫.根据乔在迷宫中的位置以及迷宫的哪个方块着火,你必 ...

  7. UVA 11624 Fire!【两点BFS】

    Joe works in a maze. Unfortunately, portions of the maze have caught on fire, and the owner of the m ...

  8. UVa 11624 Fire!(BFS)

    Fire! Time Limit: 5000MS   Memory Limit: 262144KB   64bit IO Format: %lld & %llu Description Joe ...

  9. (简单) UVA 11624 Fire! ,BFS。

    Description Joe works in a maze. Unfortunately, portions of the maze have caught on fire, and the ow ...

随机推荐

  1. 8 -- 深入使用Spring -- 2... Spring的“零配置”支持

    8.2 Spring的“零配置”支持 Spring支持使用Annotation来代替XML配置文件.

  2. OpenGL 知识二

    OpenGL综述 September 14, 2014 学习OpenGL是学习计算机图形学的一个工具,因为计算机上图形的显示要依靠底层的软件和硬件,学习图形学除了学习基本的概念,线,曲面,图形生成,变 ...

  3. WAF Bypass数据库特性(Access探索篇)

    0x01 背景 无聊,测试了一下access特性 0x02 测试 常见有5个位置即:select * from admin where id=1[位置一]union[位置二]select[位置三]1, ...

  4. Expected BEGIN_ARRAY but was BEGIN_OBJECT

    Expected BEGIN_ARRAY but was BEGIN_OBJECT at line 1 column 3519 path $.data[1].inspector_user Gson 中 ...

  5. 使用js是想防止表单重复提交的效果

    直接上代码: <html> <head> <title>Form表单</title> <script type="text/javasc ...

  6. Xcode 插件集:xTextHandler

    本文转载至 http://www.tuicool.com/articles/zIFvQn7 基于 Xcode Source Editor Extension 做了一个插件集,叫做 xTextHandl ...

  7. 合格PHP工程师的知识结构

    摘自http://www.cnblogs.com/ftx5410/p/7204672.html 一下子就想了这么多,后续想到了再补,请大家多多指教.其实编程使用什么语言不重要,最重要的是思想,编程的思 ...

  8. 【easyswoole】 解决安装报错

    在使用swoole 创建项目时候,报错 创建命令 composer create-project easyswoole/app easyswoole 错误信息: 解决办法,切换composer 源 镜 ...

  9. try except与try finally不同之处

    try except与try finally不同之处 try//尝试执行 {SomeCode}  except//出错的时候执行, Except有特定的错误类型  {SomeCode}  end; t ...

  10. java框架---->mybatis的使用(一)

    这里我们记录一些mybatis的一些常用知识和项目中遇到的问题总结.快乐人生的三个必要元素是,有要做的事.热爱的事及盼望的事. mybatis的一些知识 一.mybatis插入返回主键值 插入的jav ...