HDU 4528 小明系列故事——捉迷藏
2014-05-06 19:40
260 查看
题目链接~~>
做题感悟:这题需要逆向思维,先预处理一下就好。
解题思路:先预处理一下将可以看到 D 与 E 的点标记一下,这样 bfs()遍历迷宫时就可以节省很多时间,还要注意:可以重复走走过的点只要用二进制压缩一下就好。
代码:
做题感悟:这题需要逆向思维,先预处理一下就好。
解题思路:先预处理一下将可以看到 D 与 E 的点标记一下,这样 bfs()遍历迷宫时就可以节省很多时间,还要注意:可以重复走走过的点只要用二进制压缩一下就好。
代码:
#include<stdio.h> #include<iostream> #include<map> #include<stack> #include<string> #include<string.h> #include<stdlib.h> #include<math.h> #include<vector> #include<queue> #include<algorithm> using namespace std ; #define lld __int64 const double PI = 3.1415926 ; const double esp = 1e-4 ; const int md= 2810778 ; const int MX = 105 ; int n,m,t ; char s[MX][MX] ; bool va[MX][MX],vb[MX][MX],vis[MX][MX][5] ; int dx[4]={1,-1,0,0},dy[4]={0,0,1,-1} ; struct node { int x,y,step,key ; } ; bool search(int x,int y) // 判断边界 { if(x<0||y<0||x>=n||y>=m||s[x][y]=='X') return false ; return true ; } void init(int dx,int dy,int ex,int ey)// 预处理 { for(int i=dx+1 ;i<n ;i++) if(s[i][dy]=='.') va[i][dy]=true ; else if(s[i][dy]=='S') { va[i][dy]=true ; break ; } else break ; for(int i=dx-1 ;i>=0 ;i--) if(s[i][dy]=='.') va[i][dy]=true ; else if(s[i][dy]=='S') { va[i][dy]=true ; break ; } else break ; for(int j=dy+1 ;j<m ;j++) if(s[dx][j]=='.') va[dx][j]=true ; else if(s[dx][j]=='S') { va[dx][j]=true ; break ; } else break ; for(int j=dy-1 ;j>=0 ;j--) if(s[dx][j]=='.') va[dx][j]=true ; else if(s[dx][j]=='S') { va[dx][j]=true ; break ; } else break ; for(int i=ex+1 ;i<n ;i++) if(s[i][ey]=='.') vb[i][ey]=true ; else if(s[i][ey]=='S') { vb[i][ey]=true ; break ; } else break ; for(int i=ex-1 ;i>=0 ;i--) if(s[i][ey]=='.') vb[i][ey]=true ; else if(s[i][ey]=='S') { vb[i][ey]=true ; break ; } else break ; for(int j=ey+1 ;j<m ;j++) if(s[ex][j]=='.') vb[ex][j]=true ; else if(s[ex][j]=='S') { vb[ex][j]=true ; break ; } else break ; for(int j=ey-1 ;j>=0 ;j--) if(s[ex][j]=='.') vb[ex][j]=true ; else if(s[ex][j]=='S') { vb[ex][j]=true ; break ; } else break ; } int bfs(int x,int y) { memset(vis,false,sizeof(vis)) ; int sx,sy,key ; queue<node>q ; node curt,next ; curt.x=x ; curt.y=y ; curt.key=0 ; if(va[x][y]) curt.key=curt.key|1 ; if(vb[x][y]) curt.key=curt.key|2 ; curt.step=0 ; vis[x][y][curt.key]=true ; q.push(curt) ; while(!q.empty()) { curt=q.front() ; q.pop() ; if(curt.step>t) continue ; if(curt.key==3) // 判断是否找到两个人 return curt.step ; for(int i=0 ;i<4 ;i++) { next.x=sx=curt.x+dx[i] ; next.y=sy=curt.y+dy[i] ; next.key=key=curt.key ; next.step=curt.step+1 ; if(search(sx,sy)&&s[sx][sy]!='D'&&s[sx][sy]!='E') { if((key&1)==0&&va[sx][sy]) // 没看见过第一个人&&在这点可以看见第一个 key=key|1 ; if((key&2)==0&&vb[sx][sy]) // 没看见过第二个人&&在这点可以看见第二个人 key=key|2 ; if(!vis[sx][sy][key]) // 没有走过这点 { vis[sx][sy][key]=true ; next.key=key ; q.push(next) ; } } } } return -1 ; } int main() { int Tx,q=1 ; scanf("%d",&Tx) ; while(Tx--) { scanf("%d%d%d",&n,&m,&t) ; int dx,dy,ex,ey,sx,sy ; for(int i=0 ;i<n ;i++) { scanf("%s",s[i]) ; for(int j=0 ;j<m ;j++) { if(s[i][j]=='D') { dx=i ; dy=j ; } else if(s[i][j]=='E') { ex=i ; ey=j ; } else if(s[i][j]=='S') { sx=i ; sy=j ; } } } memset(va,false,sizeof(va)) ; memset(vb,false,sizeof(vb)) ; init(dx,dy,ex,ey) ; printf("Case %d:\n%d\n",q++,bfs(sx,sy)) ; } return 0 ; }
相关文章推荐
- hdu 4528小明系列故事——捉迷藏 (bfs)
- hdu 4528 小明系列故事——捉迷藏
- HDU-4528 小明系列故事——捉迷藏 BFS模拟
- HDU 4528 小明系列故事――捉迷藏 (很好的BFS)
- hdu 4528 小明系列故事——捉迷藏【Bfs】
- hdu 4528小明系列故事——捉迷藏
- HDU - 4528 小明系列故事——捉迷藏 (广搜)
- hdu 4528 小明系列故事——捉迷藏 bfs 解题报告
- hdu 4528——小明系列故事——捉迷藏
- HDU 4528 小明系列故事――捉迷藏
- [HDU] 4528 小明系列故事——捉迷藏 -又一个需要靠多维变量来记录一个状态访问没有被访问的广搜题
- HDU 4528 BFS 小明系列故事——捉迷藏
- 小明系列故事——捉迷藏 HDU - 4528 BFS详解
- HDU 4528 小明系列故事――捉迷藏
- BFS hdu-4528 小明系列故事——捉迷藏
- hdu 4501 小明系列故事——买年货(多维背包)
- HDU-4511 小明系列故事——女友的考验 floyd变种-标号递增最短路
- HDU 4506 小明系列故事——师兄帮帮忙【思维 快速幂 同余定理】
- HDU 4501 小明系列故事——买年货(三维背包)
- HDU--杭电--4506--小明系列故事——师兄帮帮忙--快速幂取模