HDU 1242 rescue (优先队列模板题)
Rescue
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 24205 Accepted Submission(s): 8537
Angel's friends want to save Angel. Their task is: approach Angel. We assume that "approach Angel" is to get to the position where Angel stays. When there's a guard in the grid, we must kill him (or her?) to move into the grid. We assume that we moving up, down, right, left takes us 1 unit time, and killing a guard takes 1 unit time, too. And we are strong enough to kill all the guards.
You have to calculate the minimal time to approach Angel. (We can move only UP, DOWN, LEFT and RIGHT, to the neighbor grid within bound, of course.)
Then N lines follows, every line has M characters. "." stands for road, "a" stands for Angel, and "r" stands for each of Angel's friend.
Process to the end of the file.
#.#####.
#.a#..r.
#..#x...
..#..#.#
#...##..
.#......
........
这题有很多坑点,
1朋友不止一个,所以r有多个,好解决,只要从a搜,找到第一个r结束即可
2警卫会消耗2点时间,但是队列是最先入队的, 最先入队的是步数最少的, 并不是时间最少的,所以必须要用优先队列,下面这段代码虽然AC但是是不正确的
//伪ac代码
#include<math.h>
#include<stdio.h>
#include<queue>
#include<string.h>
#include<iostream>
#include<algorithm>
using namespace std;
#define N 1234
struct point
{
int x,y,t;
}st; int n,m;
int dx[]={,-,,};
int dy[]={,,,-};
char mat[N][N];
int vis[N][N]; int bfs()
{
queue<point>q;
q.push(st);vis[st.x][st.y]=;
while(!q.empty())
{
point cur=q.front();
q.pop();
for(int i=;i<;i++)
{
point next=cur;
next.x+=dx[i];next.y+=dy[i]; if(next.x<||next.x>n||next.y<||next.y>m)continue;
if(mat[next.x][next.y]=='#'||vis[next.x][next.y]==)continue;
if(mat[next.x][next.y]=='.')next.t=next.t+;
if(mat[next.x][next.y]=='x')next.t=next.t+;
if(mat[next.x][next.y]=='r')return next.t+; q.push(next);vis[next.x][next.y]=;
}
}
return -;
}
int main()
{
while(~scanf("%d%d",&n,&m))
{
memset(vis,,sizeof(vis));
for(int i=;i<=n;i++)
for(int j=;j<=m;j++)
{
scanf(" %c",&mat[i][j]);
if(mat[i][j]=='a')
st.x=i,st.y=j,st.t=;
}
int ans=bfs();
if(ans==-)puts("Poor ANGEL has to stay in the prison all his life.");
else cout<<ans<<endl;
}
return ;
}
但面对这组数据:
2 10
axxxxxxxxr
..........
结果就不对了
这个问题能够用优先队列解决。 详见代码
优先队列版:
#include<queue>
#include<stdio.h>
#include<string.h>
#include<iostream>
using namespace std;
#define N 1234 int n, m, a, b, x, y, t, cnt, ans;
struct node
{
int x, y, time; bool operator < (const node & t)const
{
return time > t.time; //改成<号 则较大的先出队
}
}st;
priority_queue<node>q; //加上前缀 priority_ char mat[N][N];
int v[N][N];
int dx[]={, -, , };
int dy[]={, , , -}; int bfs()
{
memset(v , , sizeof(v));
while(!q.empty()) q.pop();
q.push(st);
v[st.x][st.y] = true;
while(!q.empty())
{
st = q.top(); //优先队列用q.top() 代替 q.front();
q.pop();
for(int i = ; i < ; i++)
{
node next = st;
next.x += dx[i], next.y +=dy[i];
if(v[next.x][next.y] || mat[next.x][next.y]=='#') continue;
if(next.x< || next.y< || next.x>n || next.y>m) continue;
if(mat[next.x][next.y] == '.')next.time++;
if(mat[next.x][next.y] == 'x')next.time+=;
if(mat[next.x][next.y] == 'r') return next.time+; q.push(next);
v[next.x][next.y] = true;
}
}
return -;
} int main()
{
while(cin>>n>>m)
{
for(int i = ; i <= n; i++)
for(int j = ; j <= m; j++)
{
scanf(" %c", &mat[i][j]);
if(mat[i][j] == 'a')
st.x = i, st.y = j, st.time = ;
} ans = bfs(); if(ans == -)puts("Poor ANGEL has to stay in the prison all his life.");
else cout<<ans<<endl; } return ;
} /*
7 8
#.#####.
#.a#..r.
#..#x...
..#..#.#
#...##..
.#......
........
2 10
axxxxxxxxr
..........
3 10
axxxxxxxxr
.########.
..........
*/
这个可以作为模板。
HDU 1242 rescue (优先队列模板题)的更多相关文章
- hdu 1242 Rescue
题目链接:hdu 1242 这题也是迷宫类搜索,题意说的是 'a' 表示被拯救的人,'r' 表示搜救者(注意可能有多个),'.' 表示道路(耗费一单位时间通过),'#' 表示墙壁,'x' 代表警卫(耗 ...
- HDU 2222 AC自动机模板题
题目: http://acm.hdu.edu.cn/showproblem.php?pid=2222 AC自动机模板题 我现在对AC自动机的理解还一般,就贴一下我参考学习的两篇博客的链接: http: ...
- HDU 1251 Trie树模板题
1.HDU 1251 统计难题 Trie树模板题,或者map 2.总结:用C++过了,G++就爆内存.. 题意:查找给定前缀的单词数量. #include<iostream> #incl ...
- HDU 3065 (AC自动机模板题)
题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=3065 题目大意:多个模式串,范围是大写字母.匹配串的字符范围是(0~127).问匹配串中含有哪几种模 ...
- HDU 2896 (AC自动机模板题)
题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=2896 题目大意:多个模式串.多个匹配串.其中串的字符范围是(0~127).问匹配串中含有哪几个模式串 ...
- hdu 1711 KMP算法模板题
题意:给你两个串,问你第二个串是从第一个串的什么位置開始全然匹配的? kmp裸题,复杂度O(n+m). 当一个字符串以0为起始下标时.next[i]能够描写叙述为"不为自身的最大首尾反复子串 ...
- HDU 2544 最短路(模板题)
求1到N的最短路径,模板题,以1为源点,用dijkstra算法(可以用优先级队列优化) #include <iostream> #include <algorithm> #in ...
- Number Sequence - HDU 1711(KMP模板题)
题意:给你一个a串和一个b串,问b串是否是a串的子串,如果是返回b在a中最早出现的位置,否则输出-1 分析:应该是最简单的模板题了吧..... 代码如下: ==================== ...
- 【网络流#1】hdu 3549 - 最大流模板题
因为坑了无数次队友 要开始学习网络流了,先从基础的开始,嗯~ 这道题是最大流的模板题,用来测试模板好啦~ Edmonds_Karp模板 with 前向星 时间复杂度o(V*E^2) #include& ...
- HDU 4825 Xor Sum (模板题)【01字典树】
<题目链接> 题目大意: 给定n个数,进行m次查找,每次查找输出n个数中与给定数异或结果最大的数. 解题分析: 01字典树模板题,01字典树在求解异或问题上十分高效.利用给定数据的二进制数 ...
随机推荐
- js根据银行卡号判断属于哪个银行,并返回银行缩写及银行卡类型
在做绑定银行卡,输入银行卡的时候,产品有这么一个需求,需要用户输入银行卡号的时候,显示对应的银行卡名称及简称.于是苦苦寻觅,终于找到了支付宝的开放API,银行卡校验接口 https://ccdca ...
- 基于FTP服务器搭建yum源
本例以CentOS6.8为试验对象,来搭建基于FTP服务器的yum源. 一.配置本地yum源 1.创建挂载目录/yum mkdir /yum 2.挂载镜像 mount -o loop CentOS- ...
- 【05】Number图解
[05]Number图解
- liunx 根目录介绍
1. /bin binary二进制 存放系统许多可执行程序文件 执行的相关指令,例如ls pwd whoami,后台的支持文件目录 2. /sbin super binary超级的二进制 存放系统许多 ...
- Leetcode 329.矩阵中的最长递增路径
矩阵中的最长递增路径 给定一个整数矩阵,找出最长递增路径的长度. 对于每个单元格,你可以往上,下,左,右四个方向移动. 你不能在对角线方向上移动或移动到边界外(即不允许环绕). 示例 1: 输入: n ...
- 【转】Python3学习笔记(urllib模块的使用)
原文地址:https://www.cnblogs.com/Lands-ljk/p/5447127.html 1.基本方法 urllib.request.urlopen(url, data=None, ...
- Python之窗口操作之find_window,set_foreground等
在自动化测试过程中,常常需要模拟按键的操作,比如像窗口发送一个按键,实现鼠标点击的功能,在上一篇文章中,我和大家讨论了python文件生成为不依赖与python库的exe文件的方式(需要了解的朋友戳这 ...
- 【Luogu】P2831愤怒的小鸟(手算抛物线+状压DP)
题目链接 设f[s]表示二进制集合表示下的s集合都打掉用了多少小鸟. 预处理出lne[i][j]表示i.j确定的抛物线能打掉的小鸟集合. 于是就有f[s|lne[i][j]]=min(f[s|lne[ ...
- C/C++ 程序中调用命令行命令并获取命令行输出结果
在 c/c++ 程序中,可以使用 system()函数运行命令行命令,但是只能得到该命令行的 int 型返回值,并不能获得显示结果.例如system(“ls”)只能得到0或非0,如果要获得ls的执行结 ...
- 稻草人(bzoj 4237)
Description JOI村有一片荒地,上面竖着N个稻草人,村民们每年多次在稻草人们的周围举行祭典. 有一次,JOI村的村长听到了稻草人们的启示,计划在荒地中开垦一片田地.和启示中的一样,田地需要 ...