胜利大逃亡(续)

Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 6070    Accepted Submission(s): 2096

Problem Description
Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王喜欢)……
这次魔王汲取了上次的教训,把Ignatius关在一个n*m的地牢里,并在地牢的某些地方安装了带锁的门,钥匙藏在地牢另外的某些地方。刚开始Ignatius被关在(sx,sy)的位置,离开地牢的门在(ex,ey)的位置。Ignatius每分钟只能从一个坐标走到相邻四个坐标中的其中一个。魔王每t分钟回地牢视察一次,若发现Ignatius不在原位置便把他拎回去。经过若干次的尝试,Ignatius已画出整个地牢的地图。现在请你帮他计算能否再次成功逃亡。只要在魔王下次视察之前走到出口就算离开地牢,如果魔王回来的时候刚好走到出口或还未到出口都算逃亡失败。
 
Input
每组测试数据的第一行有三个整数n,m,t(2<=n,m<=20,t>0)。接下来的n行m列为地牢的地图,其中包括:
. 代表路 * 代表墙 @ 代表Ignatius的起始位置 ^ 代表地牢的出口 A-J 代表带锁的门,对应的钥匙分别为a-j a-j 代表钥匙,对应的门分别为A-J
每组测试数据之间有一个空行。
 
Output
针对每组测试数据,如果可以成功逃亡,请输出需要多少分钟才能离开,如果不能则输出-1。
 
Sample Input
4 5 17
@A.B.
a*.*.
*..*^
c..b*
 
4 5 16
@A.B.
a*.*.
*..*^
c..b*
 
Sample Output
16
-1

 #include<stdio.h>
#include<string.h>
#include<queue>
#include<math.h>
typedef long long ll ;
const int M = + , mod = , bas = ;
char map[M][M] ;
int a[M][M][ + ] ;
int move[][] = {{,} , {-,} , {,} , {,-}} ;
int n , m , t ;
struct node
{
int x , y , step ;
int key ;
}; int bfs (int sx , int sy , int ex , int ey)
{
// puts ("heheda") ;
std::queue<node> q ;
while (!q.empty ()) q.pop () ;
node ans , tmp ;
q.push ((node) {sx , sy , ,}) ;
a[sx][sy][] = ;
while (!q.empty ()) {
ans = q.front () ; q.pop () ;
// puts ("He") ;
// printf ("s----------(%d,%d),%d\n" , (ans.x , ans.y) , ans.step) ;
if (ans.step >= t) return - ;
if (ans.x == ex &&ans.y == ey ) return a[ans.x][ans.y][ans.key];
for (int i = ; i < ; i ++) {
tmp.x = ans.x + move[i][] ; tmp.y = ans.y + move[i][] ;
if (tmp.x < || tmp.y < || tmp.x >= n || tmp.y >= m) continue ;
if (map[tmp.x][tmp.y] == '*') continue ;
char door = map[tmp.x][tmp.y] ;
if (door >= 'A' && door <= 'J' ) if ( ! (ans.key & (int)pow(,door - 'A') ) ) continue ;
tmp.step = ans.step + ;
tmp.key = ans.key ;
if (door >= 'a' && door <= 'j' ) tmp.key = tmp.key | ((int) pow ( , door - 'a')) ;
if (a[tmp.x][tmp.y][tmp.key] != - ) continue ;
a[tmp.x][tmp.y][tmp.key] = tmp.step ;
q.push (tmp) ;
}
}
return - ;
} int main ()
{
//freopen ("a.txt" , "r" , stdin );
while (scanf ("%d%d%d" , &n , &m , &t) == ) {
int x , y , ex , ey ;
// printf ("n=%d,m=%d,t=%d\n" , n , m , t ) ;
memset (a , - , sizeof(a)) ;
for (int i = ; i < n ; i ++) scanf ("%s" , map[i]) ;
for (int i = ; i < n ; i ++) {
for (int j = ; j < m ; j ++) {
if (map[i][j] == '@') {x = i , y = j ;}
else if (map[i][j] == '^') {ex = i , ey = j ;} ;
}
}
printf ("%d\n" , bfs (x , y , ex , ey) ) ;
}
return ;
}
/*
#include<stdio.h>
#include<string.h>
#include<queue>
typedef long long ll ;
const int M = 20 + 4 , mod = 1700003 , bas = 29 ;
char map[M][M] ;
int move[][2] = {{1,0} , {-1,0} , {0,1} , {0,-1}} ;
int n , m , t ;
struct node
{
int x , y , step ;
bool key[30] ;
};
struct hash
{
int w , nxt ;
int x , y , key ;
}e[mod];
int E = 0 , H[mod]; void insert (int x)
{
int y = x % mod ;
if (y < 0) y += mod ;
e[++ E].w = x ;
e[E].nxt = H[y] ;
H[y] = E ;
} bool find (int x , node tmp )
{
int y = x % mod ;
if (y < 0) y += mod ;
for (int i = H[y] ; i ; i = e[i].nxt) {
if (e[i].w == x) {
if (e[i].x == tmp.x && e[i].y == tmp.y && e[i].key)
}
}
return false ;
} int bfs (int sx , int sy , int ex , int ey)
{
std::queue<node> q ;
while (!q.empty ()) q.pop () ;
node ans , tmp ;
q.push ((node) {sx , sy , 0}) ;
while (!q.empty ()) {
ans = q.front () ; q.pop () ;
if (ans.step >= t) return -1 ;
if (ans.x == ex && ans.y == ey ) return ans.step ;
for (int i = 0 ; i < 4 ; i ++) {
tmp.x = ans.x + move[i][0] ; tmp.y = ans.y + move[i][1] ;
if (tmp.x < 0 || tmp.y < 0 || tmp.x >= n || tmp.y >= m) continue ;
if (map[tmp.x][tmp.y] == '*') continue ;
char door = map[tmp.x][tmp.y] ;
if (door >= 'A' && door <= 'J' && ans.key[door - 'A' ] == 0) continue ;
for (int j = 0 ; j < 26 ; j ++) {
tmp.key[j] = ans.key[j] ;
}
tmp.step = ans.step + 1 ;
if (door >= 'a' && door <= 'j') tmp.key[door - 'a' ] = 1 ;
ll rhs = 1 , fac = 1;
rhs = (1ll*rhs*fac + tmp.x) % mod ; fac *= 1ll*bas ; rhs = (1ll*rhs*fac+tmp.y) % mod ; fac *= 1ll*bas ;
for (int i = 0 ; i < 26 ; i ++) {
if (tmp.key[i]) {
rhs = (1ll*rhs*fac + i * i *i + i *i) % mod ;
fac *= 1ll * bas ;
}
}
if (find (rhs , tmp)) continue ;
insert (rhs , tmp) ;
q.push (tmp) ;
}
}
return -1 ;
} int main ()
{
// freopen ("a.txt" , "r" , stdin );
while (~ scanf ("%d%d%d" , &n , &m , &t) ) {
int x , y , ex , ey ;
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] == '@') {x = i , y = j ;}
else if (map[i][j] == '^') {ex = i , ey = j ;} ;
}
}
E = 0 ;
memset (H, 0 , sizeof(H)) ;
printf ("%d\n" , bfs (x , y , ex , ey) ) ;
}
return 0 ;
}
*/

一开始把x , y , key,当做hash的元素,得到一个hash值。
一直wa,后来杰神说,要更加精确的hash值,就是多加点辅助值。

so明白了,不过果然变得很麻烦,给过还是。。。。。

附上用二进制保存钥匙状态的程序。

hdu.1429.胜利大逃亡(续)(bfs + 0101011110)的更多相关文章

  1. hdu 1429 胜利大逃亡(续)(bfs+位压缩)

    胜利大逃亡(续) Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Su ...

  2. hdu - 1429 胜利大逃亡(续) (bfs状态压缩)

    http://acm.hdu.edu.cn/showproblem.php?pid=1429 终于开始能够做状态压缩的题了,虽然这只是状态压缩里面一道很简单的题. 状态压缩就是用二进制的思想来表示状态 ...

  3. hdu 1429 胜利大逃亡(续) (bfs+状态压缩)

    又开始刷题了 题意:略过. 分析:主要是确定状态量,除了坐标(x,y)之外,还有一个key状态,就好比手上拿着一串钥匙.状态可以用位运算来表示:key&(x,y)表示判断有没有这扇门的钥匙,k ...

  4. HDU 1429 胜利大逃亡(续)(bfs+状态压缩,很经典)

    传送门: http://acm.hdu.edu.cn/showproblem.php?pid=1429 胜利大逃亡(续) Time Limit: 4000/2000 MS (Java/Others)  ...

  5. hdu 1429 胜利大逃亡(续)

    题目连接 http://acm.hdu.edu.cn/showproblem.php?pid=1429 胜利大逃亡(续) Description Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王 ...

  6. HDU 1429 胜利大逃亡(续)(bfs)

    胜利大逃亡(续) Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total S ...

  7. Hdu 1429 胜利大逃亡(续) 分类: Brush Mode 2014-08-07 17:01 92人阅读 评论(0) 收藏

    胜利大逃亡(续) Time Limit : 4000/2000ms (Java/Other)   Memory Limit : 65536/32768K (Java/Other) Total Subm ...

  8. HDU 1429 胜利大逃亡(续)(DP + 状态压缩)

    胜利大逃亡(续) Problem Description Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王喜欢)…… 这次魔王汲取了上次的教训,把Ignatius关在一个n*m的地牢里,并在地牢 ...

  9. hdu 1429 胜利大逃亡(续)(bfs+状态压缩)

    Problem Description Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王喜欢)…… 这次魔王汲取了上次的教训,把Ignatius关在一个n*m的地牢里,并在地牢的某些地方安装了带 ...

随机推荐

  1. MVC5-11 浅谈拦截器

    Filter拦截器 Aop是MVC的主要设计方式之一,而微软也希望我们在使用MVC的时候更好的使用拦截器来进行切面编程.拦截器则是Mvc中的一大亮点与重点 AOP(面向切面)编程已经广泛应用在各个项目 ...

  2. CF 702B Powers of Two(暴力)

    题目链接: 传送门 Devu and Partitioning of the Array time limit per test:3 second     memory limit per test: ...

  3. Python编码格式的指定方式

    参考自: http://python.jobbole.com/85852/, 原文探究的更深,有兴趣的可以去看看. 简介来讲就是使用一种特殊的注释来声明编码格式,如何判断这种格式也用了很简单粗暴有效的 ...

  4. 【Beta版本】冲刺-Day3

    队伍:606notconnected 会议时间:12月11日 目录 一.行与思 二.站立式会议图片 三.燃尽图 四.代码Check-in 一.行与思 张斯巍(433) 今日进展:学习了很多androi ...

  5. ruby 淘宝镜像

    由于国内GFW原因,导致无法安装gem库文件.故选择淘宝镜像, 如何使用? $ gem sources --remove https://rubygems.org/ $ gem sources -a ...

  6. 更改primefaces theme

    PrimeFaces is using jQuery ThemeRoller CSS theme framework, and come with 30+ pre-designed themes th ...

  7. nosql理解

    1.NoSQL是什么? NoSQL 是 Not Only SQL 的缩写,意即"不仅仅是SQL"的意思,泛指非关系型的数据库.强调Key-Value Stores和文档数据库的优点 ...

  8. my.conf 配置编码为utf-8

    MySQL基础配置之mysql的默认字符编码的设置(my.ini设置字符编码) MySQL的默认编码是Latin1,不支持中文,那么如何修改MySQL的默认编码呢,下面以设置UTF-8为例来说明. M ...

  9. c#根据公式进行自动计算 四个5加减乘除=4

        想不出来就采用枚举法吧,代码写起来还是很简单的,当然代码写的不怎么样,也不考虑设计效率等等问题了,理论上这种类型的都可以这么拼出来,比较初级的做法,但轻松解决问题.注意Calculate(st ...

  10. Android之帮助文档

    F:\Electronic_Design\software\Android\Android_SDK_windows\adt-bundle-windows-x86-20131030\sdk\docs\r ...