http://acm.hdu.edu.cn/showproblem.php?pid=3345
题意:从起点开始向外走(上下左右) 开始时有一定的能量 进入不同的区域消耗不同的能量 能量为0不能继续行走 问可以停留在那些地方将这些地方标记为 " * "
"Y": 起点 不需要标记
".": 正常的格子 进入消耗1点能量
"T": 树 进入消耗2点能量
"R": 河 进入消耗3点能量
"#": 障碍 不能进入
"E" 敌人 不能进入 并且进入其附近(上下左右)的格子时会耗尽所有能量
"P" 朋友 进入消耗1点体力 但不能停留
输出标记后的地图
相对简单的 bfs+优先队列
代码如下:
#include <stdio.h>
#include <cstring>
#include <queue>
using namespace std;
char map[105][105];// 地图
int count[105][105];// 转换为能量消耗地图
int vis[105][105];
int N,M,X;
int x,y;
int dir[4][2]={1,0,0,1,0,-1,-1,0};
struct node{
int x;int y;
int step;
friend bool operator < (node a,node b){
return a.step<b.step;
}
};
int judge0(int i,int j){
if(i<0||j<0||i>=N||j>=M||vis[i][j]||map[i][j]=='#'||map[i][j]=='E')
return 0;
return 1;
}
int judge1(int i,int j){
if(i<0||j<0||i>=N||j>=M)
return 0;
return 1;
}
int judge2(int i,int j){
for (int k=0;k<4;k++){
int a=i+dir[k][0];
int b=j+dir[k][1];
if (judge1(a,b)&&map[a][b]=='E'){
return 1;
}
}
return 0;
}
void bfs(){
priority_queue<node> Q;
node n1,n2;
n1.x=x;
n1.y=y;
n1.step=X;
Q.push(n1);
while (!Q.empty()){
n2=Q.top();
Q.pop();
if (map[n2.x][n2.y]!='P'&&map[n2.x][n2.y]!='Y')
map[n2.x][n2.y]='*';
for (int k=0;k<4;k++){
int i=n2.x+dir[k][0];
int j=n2.y+dir[k][1];
if (judge0(i,j)){
vis[i][j]=1;
node next;
next.x=i;
next.y=j;
if(n2.step>=count[i][j]){// 如果可以走到这一个区域(存在能量不足以走到这一区域的情况)
next.step=n2.step-count[i][j];
if(judge2(i,j)){// 周围是否有敌人
next.step=-1;
}
if(next.step>=0||next.step==-1)
Q.push(next);
}
}
}
}
}
int main (){
int t;
scanf ("%d",&t);
while (t--){
scanf ("%d%d%d",&N,&M,&X);
getchar();
memset(map,0,sizeof(map));
for (int i=0;i<N;i++){
scanf ("%s",map[i]);
}
for (int i=0;i<N;i++){
for (int j=0;j<M;j++){
if (map[i][j]=='Y'){// 记住起点
x=i;
y=j;
}
// 进行能量的转换
if(map[i][j]=='.'||map[i][j]=='P')
count[i][j]=1;
else if(map[i][j]=='T')
count[i][j]=2;
else if (map[i][j]=='R')
count[i][j]=3;
}
}
memset(vis,0,sizeof(vis));
vis[x][y]=1;
bfs();
for (int i=0;i<N;i++){
printf("%s\n",map[i]);
}
putchar('\n');
}
return 0;
}