4115:鸣人和佐助
总时间限制:
1000ms
内存限制:
65536kB
描述
佐助被大蛇丸诱骗走了,鸣人在多少时间内能追上他呢?
已知一张地图(以二维矩阵的形式表示)以及佐助和鸣人的位置。地图上的每个位置都可以走到,只不过有些位置上有大蛇丸的手下,需要先打败大蛇丸的手下才能到这些位置。鸣人有一定数量的查克拉,每一个单位的查克拉可以打败一个大蛇丸的手下。假设鸣人可以往上下左右四个方向移动,每移动一个距离需要花费1个单位时间,打败大蛇丸的手下不需要时间。如果鸣人查克拉消耗完了,则只可以走到没有大蛇丸手下的位置,不可以再移动到有大蛇丸手下的位置。佐助在此期间不移动,大蛇丸的手下也不移动。请问,鸣人要追上佐助最少需要花费多少时间?
输入
输入的第一行包含三个整数:M,N,T。代表M行N列的地图和鸣人初始的查克拉数量T。0 < M,N < 200,0 ≤ T < 10
后面是M行N列的地图,其中@代表鸣人,+代表佐助。*代表通路,#代表大蛇丸的手下。
输出
输出包含一个整数R,代表鸣人追上佐助最少需要花费的时间。如果鸣人无法追上佐助,则输出-1。
样例输入
样例输入1
4 4 1
#@##
**##
###+
****
样例输入2
4 4 2
#@##
**##
###+
****
样例输出
样例输出1
6
样例输出2
4
刚开始用普通的bfs做的,(二维数组,二维标记),不知道为啥一直wa;
后来听学长讲了题;QAQ;一个经典的错误样例;
3 6 1
@#****
*#*###
***##+
正确答案应该是11;
但是二维标记答案是-1;因为二位标记是bfs找最短路,当(1,1)——>(2,1)——>(3,1)——>(3,2)——>
(3,3)——>(2,3)——>(1,3),当这样找到(1,3)时,(1,3)早已经被(1,1)——>(1,2)——>(1,3)
走过并标记了,所以这条不需要查克拉的路就走不下去了,输出-1;
用三维数组就可以避免这种情况;
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <vector>
#include <map>
#include <string>
#include <queue>
#include <stack>
#include <set>
#include <list>
#include <bitset>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
int n,m,t,sx,sy,ex,ey;
char s[210][210];
int v[210][210][10] = {0};//重点:用三维数组标记
struct id{
int x,y,s,t;//x,y是位置,s是走到这一点的步数,t是这一点拥有的查克拉的数量
id(){}
id(int a,int b,int k,int r){
x=a,y=b,s=k,t=r;
}
}ids[210];
int dx[] = {0,0,1,-1};
int dy[] = {1,-1,0,0};
int dfs(){
int nx,ny,i;
queue<id>q;
q.push(id(sx,sy,0,t));
v[sx][sy][t] = 1;
while(!q.empty()){
id k = q.front();
q.pop();
for(i = 0;i < 4;i++){
nx=k.x+dx[i],ny=k.y+dy[i];
if(nx<0||nx>=n||ny<0||ny>=m||v[nx][ny][k.t]) continue;
if(s[nx][ny] == '+'){
return k.s+1;//到达终点
}
if(s[nx][ny] == '#' && k.t>0){
v[nx][ny][k.t] = 1;
q.push(id(nx,ny,k.s+1,k.t-1));//需要一个查克拉打败大蛇丸手下
}
if(s[nx][ny] == '*'){
v[nx][ny][k.t] = 1;
q.push(id(nx,ny,k.s+1,k.t));//通路
}
}
}
return (-1);
}
int main()
{
cin >> n>>m>>t;
int i,j;
for(i = 0;i < n;i++)
for(j = 0;j < m;j++){
cin>>s[i][j];
if(s[i][j] == '@') sx=i,sy=j;//起点
if(s[i][j] == '+') ex=i,ey=j;//终点
}
cout<<dfs()<<endl;
return 0;
}