HDU 1072

题意:给你一个迷宫,2代表你当前的位置,0代表墙,1代表可走的路,3代表出口,4代表的是炸弹的重置点,一开始炸弹的倒计时设置为6,每走一步时间减少1,倒计时到0的时候走到3或者4都不可以,问走出迷宫的最小步数,没有则输出-1.

思路:dfs剪枝,这里的剪枝有点不一样,因为这里可以回溯的走,也就是可以走回头路,所以不能以走过的路来标记,这里的标记方法呢,就是以最短路径和当前位置离爆炸时间长度来标记.

 

 

#include<iostream>
#include<cstdio>
#include<cstring>
#include<climits>
using namespace std;
const int qq=10,no=1e7;
int map[qq][qq],step[qq][qq],time[qq][qq];
int n,m,tx,ty,minx,p;
void dfs(int x,int y,int cnt,int p)
{    
    if(x<0||y<0||x>=n||y>=m)    return;
    if(cnt>=minx||p<=0)    return;
    if(map[x][y]==0)    return;
    if(map[x][y]==3)    if(cnt<minx)    minx=cnt;
    if(map[x][y]==4)    p=6;
    if(cnt>=step[x][y] && time[x][y]>=p)return;  //关键标记、 
    step[x][y]=cnt;  
    time[x][y]=p; 
    dfs(x,y+1,cnt+1,p-1);
    dfs(x,y-1,cnt+1,p-1);
    dfs(x+1,y,cnt+1,p-1);
    dfs(x-1,y,cnt+1,p-1);
    return;
}
int main()
{
    int t;    cin >> t;
    while(t--){
        cin >> n >> m;
        int sx,sy;
        for(int j,i=0;i<n;++i)
            for(j=0;j<m;++j){
                cin >> map[i][j];
                if(map[i][j]==2){
                    sx=i;sy=j;
                }
                if(map[i][j]==3){
                    tx=i;ty=j;
                }
                step[i][j]=INT_MAX;
            }
            minx=no;
        dfs(sx,sy,0,6);
        if(minx==no)    cout << "-1" << endl;
        else            cout << minx << endl;
    }
}

 

posted @ 2016-01-19 10:18  我不萌、我要高冷  阅读(249)  评论(0编辑  收藏  举报