hdu1026

//BFS+优先队列(打印路径)
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<queue>

using namespace std;

const int ROW = 101;
const int COL = 101;
const int DIRS = 4;

struct priNode {
   int x, y, time;
   friend bool operator < (priNode a, priNode b) {
      return a.time > b.time;
   }
};

struct path { //存储路径
   int x, y, time;
}path[ROW][COL];

char map[ROW][COL];
int dir[DIRS][2] = {-1,0,0,1,1,0,0,-1};

bool inMap(int pi, int pj, int row, int col);
bool bfs(int pi, int pj, int row, int col, int *times);
void printPath(int times, int pi, int pj);

int main(void) {
   int n, m;
   int i, j, k;

   while (scanf("%d%d", &n, &m) != EOF) {
      for (i=0; i<n; ++i) {
         scanf("%s", map[i]);
      }

      int times = 0;
      if (bfs(0, 0, n, m, &times)) {
         printf("It takes %d seconds to reach the target position, let me show you the way.\n", times);
         printPath(times, n-1, m-1);
      }else {
         printf("God please help our poor hero.\n");
      }
      printf("FINISH\n");
   }

   return 0;
}

bool inMap(int pi, int pj, int row, int col) {
   return (pi>=0 && pi<row && pj>=0 && pj<col);
}

bool bfs(int pi, int pj, int row, int col, int *times) {
   int i;
   priNode now, next;
   priority_queue<priNode> Q;

   now.x = pi;
   now.y = pj;
   now.time = 0;
   Q.push(now);
   path[0][0].x = -1;  //起始点无前驱节点
   path[0][0].y = -1;
   path[0][0].time = 0;  

   while (!Q.empty()) {
      now = Q.top();
      Q.pop();
      
      if (now.x == row-1 && now.y == col-1) {  //到达目的地
         *times = now.time;
         return true;
      }
         
      for (i=0; i<DIRS; ++i) {
         next.x = now.x + dir[i][0];
         next.y = now.y + dir[i][1];
         if (inMap(next.x, next.y, row, col)) {
            if (map[next.x][next.y] == '.') {
               next.time = now.time + 1; 
               Q.push(next);
               path[next.x][next.y].x = now.x;  //记录路径,前驱节点
               path[next.x][next.y].y = now.y;
               path[next.x][next.y].time = 0;
               map[next.x][next.y] = 'X';
            }else if (map[next.x][next.y] != 'X') {
               next.time = now.time + (map[next.x][next.y] - '0') + 1; //打怪时间+经过时间
               Q.push(next);
               path[next.x][next.y].x = now.x;  //记录路径,前驱节点
               path[next.x][next.y].y = now.y;
               path[next.x][next.y].time = map[next.x][next.y] - '0';
               map[next.x][next.y] = 'X';
            }
         }
      }
   }
   
   return false;
}

void printPath(int times, int px, int py) {  //递归打印路径
   if (times > 0) {
      if (path[px][py].time-- != 0) {    //打怪
         printPath(times-1, px, py);
         printf("%ds:FIGHT AT (%d,%d)\n", times--, px, py);
      }else {
         printPath(times-1, path[px][py].x, path[px][py].y);
         printf("%ds:(%d,%d)->(%d,%d)\n", times--, path[px][py].x, path[px][py].y, px, py);
      }
   }
}

 

转载于:https://www.cnblogs.com/try86/archive/2013/04/09/3011084.html

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值