现在的位置: 首页 > 综合 > 正文

hdu 1010 奇偶剪枝

2013年01月10日 ⁄ 综合 ⁄ 共 1137字 ⁄ 字号 评论关闭

题意:给一个字符矩阵,S是起点,D是终点,X不能走,其它地方可以走,求T步数的时候是否能从S恰好走到T。。。

思路:开始题意理解错了,以为就是个BFS(),WA掉。。。后来看了discuss是dfs()。。TLE掉,后来上网搜,原来得加个“奇偶剪枝”的东西、、、

奇偶剪枝:http://www.cnblogs.com/newpanderking/archive/2012/10/09/2716984.html

#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#include<cmath>
using namespace std;
int dir[4][2]={{-1,0},{1,0},{0,-1},{0,1}};
char map[10][10];
int vis[10][10] , sx , sy , ex , ey , n , m , T;
bool dfs(int x , int y , int step) {
    int i , j , k;
    //printf("%d %d %d\n",x,y,step);
    int tmp;      //偏移路径 
    tmp = T - step - abs(x-ex) - abs(y-ey);
    if(tmp < 0 || tmp%2!=0) return false;   /*走最近的情况还无法到达剪枝1,奇偶剪枝2*/
    if(step == T && x == ex && y == ey) return true;
    for(k = 0 ; k < 4 ; k ++) {
        i = x + dir[k][0];
        j = y + dir[k][1];
        if(!vis[i][j] && i>=0 && i<n && j>=0 && j<m) {
            vis[i][j] = 1;
            if(dfs(i , j , step+1)) return true;  
            vis[i][j] = 0;  
        }    
    }
    return false;
}
int main() {
    int i , j;
    while(~scanf("%d%d%d",&n,&m,&T)) {
        if(!n&&!m&&!T) break;
        for(i = 0 ; i < n ; i ++)
        scanf("%s",map[i]);
        memset(vis , 0 , sizeof(vis));
        int cnt = 0;
        for(i = 0 ; i < n ; i ++) {
            for(j = 0 ; j < m ; j ++) {
                if(map[i][j]=='S') {
                    sx = i , sy = j;
                    vis[i][j] = 1;    
                } else if(map[i][j]=='D') {
                    ex = i , ey = j;    
                } else if(map[i][j]=='X') {
                    vis[i][j] = 1;
                    cnt++;
                }    
            } 
        }
        if(n*m - cnt<T) {
            printf("NO\n");        /*剪枝3*/
            continue;    
        }
        if(dfs(sx , sy , 0)) printf("YES\n");
        else printf("NO\n");
    }    
}

抱歉!评论已关闭.