点击打开链接

题意:从K走到T,S为怪,走的时候就多花费一秒,走到T时收集m把不同的钥匙。可是规定收集n之前,必须1~n-1所有收集完成,怪最多有5个

思路:怪最多就有5个,然后钥匙是1~9把,我们每一个点的状态就不会非常多,在BFS时每一个点的状态进行标记即可了。5个怪状态压缩着推断,由于这个怪在第二次经过的时候已经死了,不用花费时间去杀死它

#include <map>
#include <queue>
#include <stdio.h>
#include <iostream>
#include <string.h>
#include <stdlib.h>
#include <algorithm>
using namespace std;
typedef long long ll;
const int inf=0x3f3f3f3f;
const int maxn=110;
int sx,sy,ex,ey,n,m,cnt;
int dir[4][2]={{0,1},{0,-1},{1,0},{-1,0}};
int vis[maxn][maxn][10][40];
char str[maxn][maxn];
struct edge{
int x,y,step,numkey,ss;
};
struct snake{
int x,y;
}sna[10];
int bfs(){
queue<edge>que;
edge c,ne;
memset(vis,0,sizeof(vis));
c.x=sx,c.y=sy,c.step=0,c.numkey=0,c.ss=0;
vis[c.x][c.y][0][0]=1;
que.push(c);
int ans=inf;
while(!que.empty()){
c=que.front();que.pop();
if(c.x==ex&&c.y==ey&&c.numkey==m){
ans=min(ans,c.step);
}
for(int i=0;i<4;i++){
int xx=dir[i][0]+c.x;
int yy=dir[i][1]+c.y;
if(xx<0||xx>n-1||yy<0||yy>n-1||str[xx][yy]=='#') continue;
if(vis[xx][yy][c.numkey][c.ss]) continue;
ne.x=xx;ne.y=yy;ne.step=c.step+1;ne.numkey=c.numkey;ne.ss=c.ss;
if(str[xx][yy]>='1'&&str[xx][yy]<='9'){//假设走到的是钥匙的位置进行推断
int t=str[xx][yy]-'0';
if(ne.numkey==t-1){//钥匙刚好是当前钥匙数+1,就符合条件
ne.numkey++;
vis[ne.x][ne.y][ne.numkey][ne.ss]=1;
que.push(ne);
}else{//不符合直接压进队列
vis[ne.x][ne.y][ne.numkey][ne.ss]=1;
que.push(ne);
}
}else if(str[xx][yy]=='S'){//遇到怪进行推断
for(int i=0;i<cnt;i++){
if(xx==sna[i].x&&yy==sna[i].y){
if((ne.ss>>i)&1){//说明这个怪已经死掉了
vis[ne.x][ne.y][ne.numkey][ne.ss]=1;
que.push(ne);
}else{//没有死掉的话时间+1,状态更新
ne.step++;
ne.ss+=(1<<i);
vis[ne.x][ne.y][ne.numkey][ne.ss]=1;
que.push(ne);
}
break;
}
}
}else{
vis[ne.x][ne.y][ne.numkey][ne.ss]=1;
que.push(ne);
}
}
}
return ans;
}
int main(){
while(scanf("%d%d",&n,&m)!=-1){
if(n==0&&m==0) break;
cnt=0;
for(int i=0;i<n;i++) scanf("%s",str[i]);
for(int i=0;i<n;i++){
for(int j=0;j<n;j++){
if(str[i][j]=='K')sx=i,sy=j;
if(str[i][j]=='T')ex=i,ey=j;
if(str[i][j]=='S'){
sna[cnt].x=i,
sna[cnt++].y=j;//记录怪的位置和数量
}
}
}
int ans=bfs();
if(ans==inf) puts("impossible");
else printf("%d\n",ans);
}
return 0;
}

HDU 5025图论之BFS的更多相关文章

  1. hdu 5025 Saving Tang Monk 状态压缩dp+广搜

    作者:jostree 转载请注明出处 http://www.cnblogs.com/jostree/p/4092939.html 题目链接:hdu 5025 Saving Tang Monk 状态压缩 ...

  2. HDU 1428 漫步校园 (BFS+优先队列+记忆化搜索)

    题目地址:HDU 1428 先用BFS+优先队列求出全部点到机房的最短距离.然后用记忆化搜索去搜. 代码例如以下: #include <iostream> #include <str ...

  3. HDU 5025 (BFS+记忆化状压搜索)

    题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=5025 题目大意: 迷宫中孙悟空救唐僧,可以走回头路.必须收集完钥匙,且必须按顺序收集.迷宫中还有蛇, ...

  4. HDU 5025:Saving Tang Monk(BFS + 状压)

    http://acm.hdu.edu.cn/showproblem.php?pid=5025 Saving Tang Monk Problem Description   <Journey to ...

  5. hdu 5025 bfs+状压

    http://acm.hdu.edu.cn/showproblem.php?pid=5025 N*N矩阵 M个钥匙 K起点,T终点,S点需多花费1点且只需要一次,1-9表示9把钥匙,只有当前有I号钥匙 ...

  6. HDU 5025 Saving Tang Monk 【状态压缩BFS】

    任意门:http://acm.hdu.edu.cn/showproblem.php?pid=5025 Saving Tang Monk Time Limit: 2000/1000 MS (Java/O ...

  7. 2014 网选 广州赛区 hdu 5025 Saving Tang Monk(bfs+四维数组记录状态)

    /* 这是我做过的一道新类型的搜索题!从来没想过用四维数组记录状态! 以前做过的都是用二维的!自己的四维还是太狭隘了..... 题意:悟空救师傅 ! 在救师父之前要先把所有的钥匙找到! 每种钥匙有 k ...

  8. HDU 5025 Saving Tang Monk --BFS

    题意:给一个地图,孙悟空(K)救唐僧(T),地图中'S'表示蛇,第一次到这要杀死蛇(蛇最多5条),多花费一分钟,'1'~'m'表示m个钥匙(m<=9),孙悟空要依次拿到这m个钥匙,然后才能去救唐 ...

  9. hdu 5025 Saving Tang Monk(bfs+状态压缩)

    Description <Journey to the West>(also <Monkey>) is one of the Four Great Classical Nove ...

随机推荐

  1. jquery选择器详细说明

    jquery中选择器感觉是用的特别多并且特别方便的一个方法,今天就在这里详细的记载下大多数常用的选择器,一起学习探讨. 首先介绍的是css3的选择器,其中包括了标签选择器(div),ID选择器(#ID ...

  2. Vue.js 系列教程 3:Vue

    原文:intro-to-vue-3-vue-cli-lifecycle-hooks 译者:nzbin 这是 JavaScript 框架 Vue.js 五篇教程的第三部分.在这一部分,我们将学习 Vue ...

  3. C和指针之学习笔记(6)

    第17章 经典数据结构类型 堆栈 堆栈接口提供三种基本的操作:push.pop 和 top. Push:把一个新值压入到堆栈的顶部. Pop: 只把顶部元素从堆栈中移除,它并不返回这个值. Top: ...

  4. PHP之 xampp 安装环境

    1.安装XAMPP  需要注意以下几点: (1):必须已管理员身份运行: (2):先点击安装Apache和mysql(如果apche端口被占用,先停止服务里面的apche服务) (3):别忘记切换PH ...

  5. 【BZOJ 2306】 2306: [Ctsc2011]幸福路径 (倍增floyd)

    2306: [Ctsc2011]幸福路径 Time Limit: 10 Sec  Memory Limit: 256 MBSubmit: 912  Solved: 437 Description 有向 ...

  6. 洛谷 P1115 最大子段和

    P1115 最大子段和 题目描述 给出一段序列,选出其中连续且非空的一段使得这段和最大. 输入输出格式 输入格式: 输入文件maxsum1.in的第一行是一个正整数N,表示了序列的长度. 第2行包含N ...

  7. POJ 3904 JZYZOJ 1202 Sky Code 莫比乌斯反演 组合数

    http://poj.org/problem?id=3904   题意:给一些数,求在这些数中找出四个数互质的方案数.   莫比乌斯反演的式子有两种形式http://blog.csdn.net/out ...

  8. ContentType组件,Django缓存机制,跨域请求

    ContentType组件 解决什么问题:表的id和数据id,来唯一确定一条数据 用: 插入数据: models:content_obj = GenericForeignKey('table_id', ...

  9. [TC6194]AllWoundUp

    [TC6194]AllWoundUp 题目大意: 有\(A\)和\(B\)两个人.\(A\)在平面上游走,\(B\)会一直盯着\(A\)看,站在\(x\)轴某个位置上不动,并随着\(A\)的运动旋转身 ...

  10. object-c语言的nonatomic,assign,copy,retain的区别

    nonatomic: 非原子性访问,不加同步,多线程并发访问会提高性能.如果不加此属性,则默认是两个访问方法都为原子型事务访问.                    (atomic是Objc使用的一 ...