HDU 1026 BSF+优先队列+记录路径、

#include<iostream>
#include<cmath>
#include<cstring>
#include<cstdio>
#include<algorithm>
#include<queue>
#include<stack>
using namespace std;
const int qq=110;
const int MAX=10000;
char map[qq][qq];
int pre[qq][qq];
int a[MAX],b[MAX];
int n,m;
int dir[5][2]={0,0,1,0,-1,0,0,1,0,-1};  // 走的顺序是右,左,下,上
struct Node
{
	int x,y;
	int pre;                 // 定义来源的方向 1左 2右 3上 4下
	char mark;                  //是否存在怪兽
	int time;
	friend bool operator <(Node a,Node b)
    {
        return a.time>b.time;
    }
};
priority_queue<Node>Q;
int check(int x,int y)
{
	if(x<0||y<0||x>=n||y>=m)    //判断是否越界
		return 0;
	if(pre[x][y])           // 判断是否走过这点
		return 0;
	if(map[x][y]=='X')      // 判断是否是墙
		return 0;
	return 1;
}
void bfs()
{
	Node ans,cns;
	ans.x=0;ans.y=0;ans.pre=0;ans.time=0;ans.mark=map[0][0];
	Q.push(ans);
	while(!Q.empty()){
		cns=Q.top();
		Q.pop();
		//printf("%d %d
",cns.x,cns.y);
		if(cns.x==n-1&&cns.y==m-1){
			//printf("%d %d
",cns.x,cns.y);
			while(!Q.empty())
				Q.pop();
			Q.push(cns);
			break;
		}
		for(int i=1;i<=4;++i){
			ans.x=cns.x+dir[i][1];
			ans.y=cns.y+dir[i][0];
			if(check(ans.x,ans.y)){
				ans.mark=map[ans.x][ans.y];
				ans.pre=i;
				pre[ans.x][ans.y]=i;
				if(map[ans.x][ans.y]>='1'&&map[ans.x][ans.y]<='9')
					ans.time=cns.time+1+(map[ans.x][ans.y]-'0');
				else
					ans.time=cns.time+1;
				Q.push(ans);
			}
		}
	}
	return;
}
void out()
{
	Node ans;
	ans=Q.top();
	Q.pop();
	printf("It takes %d seconds to reach the target position, let me show you the way.
",ans.time);
	int r=1;
	a[0]=ans.x;b[0]=ans.y;
	int x=ans.x,y=ans.y;
	//printf("%d %d
",x,y);
	while(x!=0||y!=0){      // x和y搞反了 调了两个小时、 真特么醉了
		if(pre[x][y]==1)
			y=y-1;
		else if(pre[x][y]==2)
			y=y+1;
		else if(pre[x][y]==3)
			x=x-1;
		else if(pre[x][y]==4)
			x=x+1;
		a[r]=x;b[r++]=y;
	//	printf("%d %d
",x,y);
	}
	int t=1; 
	for(int i=r-2;i>=0;--i){
		printf("%ds:(%d,%d)->(%d,%d)
",t++,a[i+1],b[i+1],a[i],b[i]);
		if(map[a[i]][b[i]]>='1'&&map[a[i]][b[i]]<='9')
			for(int j=0;j<map[a[i]][b[i]]-'0';++j)
				printf("%ds:FIGHT AT (%d,%d)
",t++,a[i],b[i]);
	}
}
int main()
{
	while(~scanf("%d %d",&n,&m)){
		memset(pre,0,sizeof(pre));
		memset(a,0,sizeof(a));
		memset(b,0,sizeof(b));
		for(int i=0;i<n;++i)
			scanf("%s",map[i]);
		bfs();
		if(Q.empty())   printf("God please help our poor hero.
");
		else        	out();
		printf("FINISH
");
		while(!Q.empty())
			Q.pop();
	}
	return 0;
}
//   记录路径的数组开小了、又调了好久!!QAQ 
原文地址:https://www.cnblogs.com/sasuke-/p/5262649.html