HDU 2653 BFS+优先队列
来源:互联网 发布:高考状元笔记淘宝 编辑:程序博客网 时间:2024/04/29 01:52
/* 这题题意:告诉起点Y的位置,然后告诉终点L的位置,然后输入 n, m, t ,p,其中 n和m是代表行和列,而t 是时间,p代表能量,如果在t范围内没有找到L的话,就失败了,如果在t范围内找到了L,那么求出最少步数, .代表空地,可以走路过去,也可以飞过去,#代表不能走路过去,也不能飞过去,而@代表的是可以飞过去,但不能 走路过去,所以要广搜的同时要用到优先队列, 解题思路: BFS+优先队列 我们可以先判断能不能飞过去,因为飞过去用的步数少,然后再考虑能不能走路过去 走路过去的条件是,没有走过,然后当前所在的位置和即将要走的位置不能是‘@’,不然 走下去根本没有意义*/#include <iostream>#include <cstdio>#include <cstring>#include <queue>#include <algorithm>using namespace std;const int N=85;int n,m,t,p;char s[N][N];int dir[4][2]= {{0,1},{0,-1},{1,0},{-1,0}};bool visit[N][N][N];struct node{ int x,y,step,pow; bool friend operator <(node a,node b) { return a.step>b.step; }};node start;int bfs(int x,int y) { int i; priority_queue<node>q; node cur,next; cur.x=x; cur.y=y; cur.step=0; cur.pow=p; visit[x][y][p]=1; q.push(cur); while(!q.empty()) { cur=q.top(); q.pop(); if(cur.step>t)return -1; if(s[cur.x][cur.y]=='L')return cur.step; for(i=0; i<4; i++) { next.x=cur.x+dir[i][0]; next.y=cur.y+dir[i][1]; if(next.x<0||next.x>=n||next.y<0||next.y>=m||s[next.x][next.y]=='#')continue; if(cur.pow>0&&!visit[next.x][next.y][cur.pow-1]) { visit[next.x][next.y][cur.pow-1]=1; next.pow=cur.pow-1; next.step=cur.step+1; q.push(next); } if(s[cur.x][cur.y]!='@'&&s[next.x][next.y]!='@'&&!visit[next.x][next.y][cur.pow]) { visit[next.x][next.y][cur.pow]=1; next.pow=cur.pow; next.step=cur.step+2; q.push(next); } } } return -1;}int main() { int tcase=0,i,j,flag; while(scanf("%d%d%d%d",&n,&m,&t,&p)!=EOF) { flag=0; memset(s,0,sizeof(s)); for(i=0; i<n; i++) scanf("%s",&s[i]); for(i=0; i<n; i++) { for(j=0; j<m; j++) { if(s[i][j]=='Y') { start.x=i; start.y=j; flag=1; break; } } if(flag)break; } memset(visit,0,sizeof(visit)); int num; num=bfs(start.x,start.y); printf("Case %d:\n",++tcase); if(num==-1) printf("Poor Yifenfei, he has to wait another ten thousand years.\n"); else printf("Yes, Yifenfei will kill Lemon at %d sec.\n",num); } return 0;}