HDU1429 - 胜利大逃亡(续)

与上一道题:HDU1885 - Key Task基本没什么两样

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <algorithm>
 4 #include <cstring>
 5 #include <string>
 6 #include <queue>
 7 #include <cctype>
 8 using namespace std;
 9 const int maxn = 25;
10 int n, m, fail;
11 char G[maxn][maxn];
12 int vis[maxn][maxn][2000];
13 const int dr[] = {-1, 0, 1, 0};
14 const int dc[] = { 0, 1, 0,-1};
15
16 struct Node
17 {
18     int r, c, key, step;
19     Node(int r = 0, int c = 0, int key = 0, int step = 0):r(r), c(c), key(key), step(step){}
20 };
21
22 bool isInside(int r, int c)
23 {
24     if(r > 0 && r <= n && c > 0 && c <= m && G[r][c] != ‘*‘)
25         return true;
26     else
27         return false;
28 }
29
30 void bfs(int rr, int cc)
31 {
32     queue<Node> q;
33     memset(vis, 0, sizeof vis);
34     Node node(rr, cc, 0, 0);
35     q.push(node);
36     while(!q.empty()) {
37         Node u = q.front();
38         q.pop();
39         if(G[u.r][u.c] == ‘^‘) {
40             if(u.step < fail)
41                 printf("%d\n", u.step);
42             else
43                 printf("-1\n");
44             return;
45         }
46         for(int i = 0; i < 4; i++) {
47             Node v(u.r + dr[i], u.c + dc[i], u.key, u.step+1);
48             if(isInside(v.r, v.c)) {
49                 if(islower(G[v.r][v.c])) {
50                     int k = G[v.r][v.c] - ‘a‘;
51                     if((v.key & (1 << k)) == 0) {
52                         v.key += (1 << k);
53                     }
54                     if(!vis[v.r][v.c][v.key]) {
55                         vis[v.r][v.c][v.key] = 1;
56                         q.push(v);
57                     }
58                 }
59                 else if(isupper(G[v.r][v.c])) {
60                     int k = G[v.r][v.c] - ‘A‘;
61                     if(v.key & (1 << k) && !vis[v.r][v.c][v.key]) {
62                         vis[v.r][v.c][v.key] = 1;
63                         q.push(v);
64                     }
65                 }
66                 else {
67                     if(!vis[v.r][v.c][v.key]) {
68                         vis[v.r][v.c][v.key] = 1;
69                         q.push(v);
70                     }
71                 }
72             }
73         }
74     }
75     printf("-1\n");
76 }
77 int main()
78 {
79    // freopen("in.txt", "r", stdin);
80     while(scanf("%d %d %d", &n, &m, &fail) != EOF) {
81         memset(G, ‘*‘, sizeof G);
82         int x, y;
83         for(int i = 1; i <= n; i++) {
84             scanf("%s", G[i]+1);
85             G[i][m+1] = ‘*‘;
86             G[i][m+2] = ‘\0‘;
87             if(strchr(G[i], ‘@‘)) {
88                 x = i;
89                 y = strchr(G[i], ‘@‘) - *G - i*25;
90             }
91         }
92         //printf("%d %d\n", x, y);
93         bfs(x, y);
94     }
95     return 0;
96 }
时间: 2024-10-11 05:03:08

HDU1429 - 胜利大逃亡(续)的相关文章

hdu-1429 胜利大逃亡(续)

http://acm.hdu.edu.cn/showproblem.php?pid=1429 第一次接触搜索+状态压缩    看了大神的题解  勉强把题目弄懂了. 用二进制来表示手头的钥匙有哪些,100表示有第三把钥匙,111表示有第三.二.一把,搜索下一点时,如果该点为钥匙点,则可采用|运算来 模拟拾取,显然0001 | 1000 = 1001,同理,当为相应的门时采用&运算来模拟开启,例如1101 & 0001 = 0001(即可以打开'A'门) #include<cstdio&

hdu1429胜利大逃亡(续) (状态压缩+BFS)

Problem Description Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王喜欢)-- 这次魔王汲取了上次的教训,把Ignatius关在一个n*m的地牢里,并在地牢的某些地方安装了带锁的门,钥匙藏在地牢另外的某些地方.刚开始Ignatius被关在(sx,sy)的位置,离开地牢的门在(ex,ey)的位置.Ignatius每分钟只能从一个坐标走到相邻四个坐标中的其中一个.魔王每t分钟回地牢视察一次,若发现Ignatius不在原位置便把他拎回去.经过若干次的尝试,Ignatius已画

hdu1429胜利大逃亡(续)(状态压缩+bfs)

题目链接: 啊哈哈,点我点我 题意及思路 最开始我以为跟普通的bfs一样,所以直接写了一个朴素的bfs,一跑,前两组数据对了,但是第三组不对,一看,走过的还可以走啊,所以不能标记,结果我的bfs乱改,最后 毫无疑问改成了死循环.所以看题解... 思路:因为有10中不同的钥匙,每种都有两种状态,所以结合计算机是二进制保存的特点,刚好把这10把钥匙当成每一个为,要要1<<10个位保存所有的状态,然后就是模拟捡起钥匙,捡起钥匙就是说明这个位上的数字变成1这个状态,所以自然而然想到了位运算,只要|一下

HDU1429 胜利大逃亡(续) BFS +简单状压

把手中持有的钥匙状态状压一下即可,然后vis访问标记的时候,开个三维,多一维即为当前持有钥匙状态,这样就能祛除重复标记困难走点的问题,跟网络赛那题很像,网络赛的更难点,这个简单点 int n,m,t; int sx,sy,ex,ey; char mp[20 + 55][20 + 55]; bool vis[20 + 5][20 + 5][(1<<10) + 5]; int dir[4][2] = {{1,0},{0,1},{-1,0},{0,-1}}; struct Node { int no

HDU1429 胜利大逃亡(续)(BFS+状态压缩)

题目链接:点击打开链接 题意:迷宫中,一个起点,一个终点,迷宫中有墙,有门,门的钥匙也在迷宫中某处,只有拿到钥匙才能打开门,问能不能再T步(不含)之内逃出迷宫. 题解:在朴素BFS上增加了钥匙的状态,只有有钥匙才能打开门,总共有不超过10吧钥匙,所以用一个int的整数的二进制即可存储钥匙的状态.碰到门先判断状态,碰到钥匙更新状态. 代码: #include<iostream> #include<cstdio> #include<cstring> #include<

HDU1429胜利大逃亡(续)BFS+状态压缩

这题的算是BFS中应用状压的一个模板题吧,没啥难度,用key来存储已获得的钥匙,状压一下就可以了 不过我写的过程中,犯了好多SB错误,导致调试了好久才A,本来仔细可以1A的说 #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> #include <climits> #include <string> #include <iostre

胜利大逃亡(续)(状态压缩bfs)

胜利大逃亡(续) Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 7357    Accepted Submission(s): 2552 Problem Description Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王喜欢)……这次魔王汲取了上次的教训,把Ignatius关在一个n*m的地牢里,并在地牢的某些地方安装了带

HDOJ 题目1429 胜利大逃亡(续)(BFS)

New! 关于举办校第十五届程序设计竞赛暨2015省赛集训队选拔赛的通知 胜利大逃亡(续) Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 5811    Accepted Submission(s): 2027 Problem Description Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王喜欢)-- 这次魔王汲取了上次

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

胜利大逃亡(续) Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 6270    Accepted Submission(s): 2177 Problem Description Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王喜欢)-- 这次魔王汲取了上次的教训,把Ignatius关在一个n*m的地牢里,并在地牢的某些地方安装了

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

胜利大逃亡(续) Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 7346    Accepted Submission(s): 2546 Problem Description Ignatius再次被魔王抓走了(搞不懂他咋这么讨魔王喜欢)…… 这次魔王汲取了上次的教训,把Ignatius关在一个n*m的地牢里,并在地牢的某些地方安装了带