HDOJ 1242 Rescue (BFS+优先队列)

来源:互联网 发布:差额计算法步骤 编辑:程序博客网 时间:2024/05/17 08:29

 http://acm.hdu.edu.cn/showproblem.php?pid=1242

题意:天使被关入了恶魔的监狱,他的朋友们要救他出去,根据给出的“地图“求他的朋友们到达他的位置的最短时间,路途中每走一个格子花费1个单位的时间,遇到守卫者需要再花1个单位的时间把他打倒……

思路:因为朋友不止一个,要从每个朋友出发既要储存每个朋友的初始位置,又要进行多次BFS,极其浪费时间。所以,应该从天使出发找朋友。由于这道题有守卫的存在,最短时间不等于最小步数了,所以不可以用队列了,而要使用优先队列。

BFS时,求最短步数可以用队列;如果每一步有权值且不全为1时,则需要使用优先队列。

#include<cstdio>#include<cstring>#include<climits>#include<queue>using namespace std;struct node{int x,y,cnt;friend bool operator < (node a,node b) {    return a.cnt>b.cnt; //小的在前面}};int map[222][222];int n,m,min=INT_MAX;int dx[]={-1,1,0,0},dy[]={0,0,-1,1};struct node begin;int bfs(){int i,x,y;struct node now,next;priority_queue <struct node> q;q.push(begin);while(!q.empty()){now=q.top();q.pop();for(i=0;i<4;i++){x=now.x+dx[i];y=now.y+dy[i];if(map[x][y]==-1)return now.cnt+1;if(x>0&&x<=n&&y>0&&y<=m&&(!map[x][y]||map[x][y]==2)){next.x=x;next.y=y;next.cnt=!map[x][y]?now.cnt+1:now.cnt+2;q.push(next);map[x][y]=1;}}}return -1;}int main(){int i,j,ans;char c;while(scanf("%d %d",&n,&m)==2){memset(map,0,sizeof(map));for(i=1;i<=n;i++){getchar();for(j=1;j<=m;j++){scanf("%c",&c);if(c=='.')map[i][j]=0;else if(c=='#')map[i][j]=1;else if(c=='x')map[i][j]=2;else if(c=='r'){map[i][j]=-1;}else if(c=='a'){map[i][j]=1;begin.x=i;begin.y=j;begin.cnt=0;}}}ans=bfs();if(ans<0)printf("Poor ANGEL has to stay in the prison all his life.\n");elseprintf("%d\n",ans);}return 0;}