题目链接:hdu 1010 Tempter of the Bone(dfs+剪枝)
题意:狗狗从S出发,要在正好t秒的时候到达D,每一块地只能走一次,X代表墙不能走,问能否到达
思路:深搜,但是需要剪枝,每走一步,判断能否在剩下的时间中不考虑墙通过最短的路到达出口,若不能直接返回。
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<iostream>
using namespace std;
typedef long long ll;
char s[10][10];
int vis[10][10];
int nxt[4][2]={0,1,0,-1,1,0,-1,0};
int sx,sy,ex,ey;
int n,m,t;
int flag;
bool judge(int i,int j){
if(i<0||i>=n||j<0||j>=m||(s[i][j]=='X')||vis[i][j])return 0;
return 1;
}
void dfs(int x,int y,int time){
if((x==ex)&&(y==ey)){
if(time==t)flag=1;
return ;
}
if(time>=t)return ;
if((t-time)<(abs(x-ex)+abs(y-ey)))return ;
int nx,ny;
for(int i=0;i<4;i++){
nx=x+nxt[i][0];
ny=y+nxt[i][1];
if(!judge(nx,ny))continue;
vis[nx][ny]=1;
dfs(nx,ny,time+1);
vis[nx][ny]=0;//不成功要记得还原vis
if(flag)return ;
}
}
int main(){
while(~scanf("%d%d%d",&n,&m,&t)){
if(!n&&!m&&!t)break;
for(int i=0;i<n;i++){
scanf("%s",s[i]);
}
for(int i=0;i<n;i++){
for(int j=0;j<m;j++){
if(s[i][j]=='S'){
sx=i;sy=j;
}
if(s[i][j]=='D'){
ex=i;ey=j;
}
}
}
memset(vis,0,sizeof(vis));
flag=0;
vis[sx][sy]=1;
dfs(sx,sy,0);
if(flag)printf("YES\n");
else printf("NO\n");
}
return 0;
}