最近WS因差1分钟没能AK而深受打击,自(bi)暴(guan)自(xiu)弃(lian),沉迷英雄(shua)联盟(ti)无法自拔,有天WS突发奇想,准备开发一款英雄联盟版的迷宫游戏,游戏规则如下:

英雄盖伦出生在迷宫的某处,盖伦可往前后左右四个方向走动,每走一步用时为1(也可停止不动),盖伦带有技能闪现,使用闪现可以穿过1个厚度的墙(耗时为1,穿完墙落地开始闪现进入CD),闪现技能CD为p,迷宫中随机分布0-3个蓝爸爸,经过蓝爸爸时可以选择打或者不打,击杀蓝爸爸消耗1单位时间并可获得蓝buff(蓝爸爸不会复活),蓝buff持续时间为q,buff持续时间内使用闪现技能CD减半(向下取整,如果我击杀蓝buff时候技能还处于cd状态cd不会减半),多个蓝buff时间可叠加。请写出一个程序求出盖伦走出迷宫所需的最小时间。

ps:buff剩一秒时穿墙后闪现CD按原CD计算。

Input

‌输入包含多个测试下样例,每个样例的第一行包含4个整数m,n,p,q。分别表示迷宫的长,宽,闪现CD,每个蓝buff持续时间,1<=m,n<=20,1<=p,q<=10。接下来的m行为迷宫分布,#表示墙,.表示路,@表示蓝爸爸,S表示英雄出生点,E表示迷宫出口。
‌(测试数据保证至少有一条路可以通向出口)

Output

‌输出一个数字表示盖伦走出迷宫所需的最小时间

SampleInput
1 10 1 5
S.#..#..#E1 10 2 5
S.#..#..#E1 10 2 5
S@#..#..#E

SampleOutput
6
8
7

思路:主要是不好保存状态,可以用五维数组,分别保存坐标,cd,buff时间,以及记录哪些蓝buff是打过的,最不好保存的是哪些蓝buff打过,由于蓝buff只有打过和没打过两种状态,可以考虑用二进制来保存,每个二进制位的1或0表示该蓝buff是否打过。注意一种特殊情况:S.#@#.#.#.#.#E,我到达蓝buff时,可以先等待几秒,等到CD快没了的时候再打蓝buff。

#include <stdio.h>
#include <string.h>
#include <queue>
using namespace std;const int maxn = 25;
char mat[maxn][maxn];
bool vis[25][25][12][12][8];
int dir[4][2] = {{1,0},{-1,0},{0,1},{0,-1}};
int m,n,p,q;struct node
{int x,y,cd,buff,mark,time;
}st,ed;int check(node a)
{if (a.x < 0 || a.x >= n || a.y < 0 || a.y >= m) return 0;return 1;
}int bfs()
{memset(vis,false,sizeof(vis));queue <node> Q; st.cd = st.buff = st.mark = st.time = 0;Q.push(st);vis[st.x][st.y][st.cd][st.buff][st.mark] = true;node now,next;while (!Q.empty()){now = Q.front();Q.pop();if (now.x == ed.x && now.y == ed.y) return now.time;next = now;if (mat[now.x][now.y] >= 0 && mat[now.x][now.y] <= 2)//判断是否为蓝buff {if ((now.mark & (1 << mat[now.x][now.y])) == 0)//判断该蓝buff是否打过 {next.mark += 1 << mat[now.x][now.y];//将该蓝buff标记为打过 next.time++;next.cd = next.cd > 0 ? next.cd - 1 : 0;next.buff = next.buff > 0 ? next.buff - 1 : 0;next.buff += q;if (!vis[next.x][next.y][next.cd][next.buff][next.mark]){Q.push(next);vis[next.x][next.y][next.cd][next.buff][next.mark] = true;}}}next = now;if (now.cd > 0 || now.buff > 0)//前面提到的原地等待CD的情况,这里还考虑了 {                             //原地消耗蓝buff时间的情况(暂时不知道是否有用) next.cd = next.cd > 0 ? next.cd - 1 : 0;next.buff = next.buff > 0 ? next.buff - 1 : 0;next.time++;if (!vis[next.x][next.y][next.cd][next.buff][next.mark]){Q.push(next);vis[next.x][next.y][next.cd][next.buff][next.mark] = true;}}for (int i = 0; i < 4; i++){next = now;next.x += dir[i][0];next.y += dir[i][1];if (!check(next)) continue;if (mat[next.x][next.y] == '#')//使用闪现穿墙 {if (next.cd > 0) continue;next.x += dir[i][0];next.y += dir[i][1];if (!check(next) || mat[next.x][next.y] == '#') continue;if (next.buff > 1) next.cd = p/2;//有buff则CD时间减半 else next.cd = p;next.buff = next.buff > 0 ? next.buff - 1 : 0;next.time++;if (!vis[next.x][next.y][next.cd][next.buff][next.mark]){Q.push(next);vis[next.x][next.y][next.cd][next.buff][next.mark] = true;}              }else{next.cd = next.cd > 0 ? next.cd - 1 : 0;next.buff = next.buff > 0 ? next.buff - 1 : 0;next.time++;if (!vis[next.x][next.y][next.cd][next.buff][next.mark]){Q.push(next);vis[next.x][next.y][next.cd][next.buff][next.mark] = true;}}}}return 0;
}int main()
{while (scanf("%d%d%d%d",&n,&m,&p,&q) != EOF){for (int i = 0; i < n; i++)scanf("%s",mat[i]);int id = 0;for (int i = 0; i < n; i++){for (int j = 0; j < m; j++){if (mat[i][j] == 'S'){st.x = i;st.y = j;}if (mat[i][j] == 'E'){ed.x = i;ed.y = j;}if (mat[i][j] == '@'){mat[i][j] = id++;//为每个蓝buff编号 }}}printf("%d\n",bfs());}    return 0;
}

2018年四校联合周赛-第三场(新手场) D 盖伦快跑相关推荐

  1. 2018六校联合周赛上学期第一场-我来爆零啦 寻找中位数 kth

    题目链接 寻找中位数 TimeLimit:1000MS  MemoryLimit:128MB 64-bit integer IO format:%lld Problem Description 这题温 ...

  2. 牛客网暑期ACM多校训练营(第三场)

    牛客网暑期ACM多校训练营(第三场) A. PACM Team 01背包,输出方案,用bool存每种状态下用的哪一个物品,卡内存.官方题解上,说用char或者short就行了.还有一种做法是把用的物品 ...

  3. 2019牛客暑期多校训练营(第三场)H.Magic Line

    2019牛客暑期多校训练营(第三场)H.Magic Line 题目链接 题目描述 There are always some problems that seem simple but is diff ...

  4. 2020牛客暑期多校训练营(第三场)A.Clam and Fish

    2020牛客暑期多校训练营(第三场)A.Clam and Fish 题目链接 题目描述 There is a fishing game as following: The game contains ...

  5. 2018六校联合校赛-1st-买手机

    题目描述: 阿Jun是个小屏手机爱好者,他拒绝一切带有plus和note字眼的手机,而他一直使用的是一部美国苹果公司出品的iPhoneSE. 可惜的是,有一次阿Jun在洗手间洗手,不小心手一抖,手机掉 ...

  6. 职场小说:《米亚快跑》PDF版下载

    这是一部奇特有趣的女性职场小说,不陷入目前市场上任何一部职场小说的窠臼,不大惊小怪地描述外企优越感,不涉及耸人听闻的职场阴谋,不触碰自说自话的情感纠葛-- 米娅,一个有点二百五,有点唠叨的姑娘,毕业于 ...

  7. HDU 2019 Multi-University Training Contest 1 杭电2019多校联合训练赛 第一场 1001 Blank (6578)

    HDU 2019 Multi-University Training Contest 1 杭电2019暑期多校集训第一场 1001 Blank (6578) Problem Description T ...

  8. 暑假N天乐【比赛篇】 —— 2019牛客暑期多校训练营(第三场)

    这场相对来说友好一点,本来前几天就补差不多了,然后忘记发了... 以下题解包括:\(A \ \ \ B \ \ \ F \ \ \ G \ \ \ H \ \ \ J\) \(D\) 题队友补了,我也 ...

  9. 2013多校训练赛第三场 总结

    HDU 4621~4631 今天的多校好变态,是IOI冠军出的题,把我们虐的半死了. 简单讲一下今天的情况,今天就只做了两道水题,算是签了个到,然后就卡1011(HDU 4631)一个下午了.其实感觉 ...

最新文章

  1. 使用openssl给web站点颁发证书
  2. XDOJ-1093-一元三次方程
  3. 数据结构与算法17-表插入排序
  4. Ionic APP 热更新 之 产品发布状态下的热更新搭建,去local-dev-addon插件
  5. 3.等待和通知(Waiting and Notification)
  6. DFX 9.303 for QQMusic 2010
  7. scrt_sfx安装
  8. java 主类 测试类_Java中的测试类和主类分别是什么,有点晕啊。?
  9. ibatis 大于等于小于等于的写法
  10. Ubuntu使用问题备忘录
  11. 2012年8月编程语言排行榜
  12. I am Groot java题解
  13. 所谓资本寒冬,不过是一厢情愿的破灭
  14. 【Selenium】Selenium的3种等待方式
  15. org.springframework.data.mapping.PropertyReferenceException: No property item found for type BItem!
  16. Windows10应用程序无法正常启动Oxc000007b 实用解决方法
  17. C语言:求高次方数的尾数
  18. 数据帧、数据包、数据报三者区分
  19. Swift 与OC转换
  20. Oracle数据库中processes参数设置

热门文章

  1. time()函数的用法
  2. logit回归模型_常见机器学习模型的假设
  3. python中display函数_Python-函数基础总结与内置函数
  4. MyEclipse 使用技巧
  5. 软件测试工具Fiddler的使用
  6. 浏览器F12查看项目源码
  7. eNSP 动态路由(RIP)
  8. iOS原生App与H5页面交互 离线缓存 笔记
  9. [吐槽][mellanox]RoCE的默认打开;rdma-core
  10. 局部变量,全局变量(外部变量),静态局部变量,静态全局变量