zoukankan      html  css  js  c++  java
  • poj 1475 (bfs+bfs)

    bfs套一个bfs

    先bfs box的移动情况,这里注意的是可能一个坐标x,ybox多次经过是可行的。网上的很多AC代码就没注意这个。比如下面这组数据:

    8 9
    #########
    #......T#
    #.S.....#
    ##B######
    #.......#
    #.......#
    #.......#
    #########

    网上很多AC代码输出“Impossible.”明显错的。。。

    然后在每次bfs box的时候bfs person 判断是否能走到相应的点。(即相反的方向点)

    最后还注意的是 Output a single blank line after each test case. 如果最后没有空行竟然是报wa的。。。

    View Code
      1 #include <iostream>
      2 #include <cstring>
      3 #include <cstdio>
      4 #include <algorithm>
      5 #include <queue>
      6 #include <string>
      7 
      8 using namespace std;
      9 
     10 #define MAXN 22
     11 char P[4]={'N','S','W','E'};
     12 char M[4]={'n','s','w','e'};
     13 int R,C;
     14 int dir[4][2]={-1,0,1,0,0,-1,0,1};
     15 char map[MAXN][MAXN];
     16 struct point
     17 {
     18     int x,y;
     19     int p_x,p_y;//当前状态person所在的地方
     20     string ans;
     21 };
     22 bool isok(int x,int y)
     23 {
     24     if(x>=0 && x<R && y>=0 && y<C && map[x][y] != '#')
     25         return true;
     26     return false;
     27 }
     28 string tmp;
     29 bool bfs_person(point en,point cu)
     30 {
     31     tmp="";
     32     point st;
     33     st.x=en.p_x;
     34     st.y=en.p_y;
     35     st.ans="";
     36     queue<point>q;
     37     bool vis[MAXN][MAXN];
     38     memset(vis,0,sizeof(vis));
     39     while(!q.empty())
     40         q.pop();
     41     q.push(st);
     42     while(!q.empty())
     43     {
     44         point cur,next;
     45         cur=q.front();
     46         q.pop();
     47         if(cur.x==en.x && cur.y==en.y)
     48         {
     49             tmp=cur.ans;
     50             return true;
     51         }
     52         for(int i=0;i<4;i++)
     53         {
     54             next=cur;
     55             next.x=cur.x+dir[i][0];
     56             next.y=cur.y+dir[i][1];
     57             if(!isok(next.x,next.y)) continue;
     58             if(next.x==cu.x && next.y==cu.y) continue;
     59             if(vis[next.x][next.y]) continue;
     60             vis[next.x][next.y]=1;
     61             next.ans=cur.ans+M[i];
     62             q.push(next);
     63         }
     64     }
     65     return false;
     66 }
     67 string bfs_box()
     68 {
     69     bool vis[MAXN][MAXN][4];//某点四个方向是否访问!!0==N,1==S,2==W,3==E
     70     point st;
     71     st.x=st.y=-1;
     72     st.p_x=st.p_y=-1;
     73     st.ans="";
     74     for(int i=0;i<R && (st.x==-1 || st.p_x==-1);i++)
     75         for(int j=0;j<C && (st.x==-1 || st.p_x==-1);j++)
     76             if(map[i][j]=='B')
     77             {
     78                 st.x=i;
     79                 st.y=j;
     80                 map[i][j]='.';
     81             }
     82             else if(map[i][j]=='S')
     83             {
     84                 st.p_x=i;
     85                 st.p_y=j;
     86                 map[i][j]='.';
     87             }
     88     //----------------------------------------
     89     //cout<<"st.x="<<st.x<<" st.y="<<st.y<<" st.p_x="<<st.p_x<<" st.p_y="<<st.p_y<<endl;
     90     //----------------------------------------
     91     queue<point> q;
     92     while(!q.empty())
     93         q.pop();
     94     q.push(st);
     95     memset(vis,0,sizeof(vis));
     96     while(!q.empty())
     97     {
     98         point cur=q.front();q.pop();    
     99         //----------------------------------------
    100     //        cout<<"cur.x="<<cur.x<<" cur.y="<<cur.y<<" cur.p_x="<<cur.p_x<<" cur.p_y="<<cur.p_y<<endl;
    101     //    cout<<"-----------------------------\n";
    102         //----------------------------------------
    103         point next,pre;
    104         if(map[cur.x][cur.y]=='T')
    105             return cur.ans;
    106         for(int i=0;i<4;i++)
    107         {
    108             next=cur;
    109             next.x=cur.x+dir[i][0];
    110             next.y=cur.y+dir[i][1];
    111             if(!isok(next.x,next.y))
    112                 continue;
    113             if(vis[next.x][next.y][i])
    114                 continue;
    115             pre=cur;
    116             switch(i)
    117             {
    118                 case 0: pre.x=cur.x+1;break;
    119                 case 1: pre.x=cur.x-1;break;
    120                 case 2: pre.y=cur.y+1;break;
    121                 case 3: pre.y=cur.y-1;break;
    122             }
    123             if(!bfs_person(pre,cur))//搜寻人是否能走到特定的位置
    124                 continue;
    125             vis[next.x][next.y][i]=1;
    126             next.ans=cur.ans+tmp;
    127             next.ans=next.ans+P[i];
    128             next.p_x=cur.x;next.p_y=cur.y;
    129             q.push(next);
    130         }
    131     }
    132     return "Impossible.";
    133 }
    134 
    135 int main()
    136 {
    137     int cas=1;
    138     while(scanf("%d%d",&R,&C) && (R+C))
    139     {
    140         getchar();
    141         for(int i=0;i<R;i++)
    142             gets(map[i]);
    143 
    144         //---------------------------------------
    145     //    for(int i=0;i<R;i++)
    146         //    cout<<map[i]<<endl;
    147         //----------------------------------------
    148 
    149         printf("Maze #%d\n",cas++);
    150         //printf("%s\n",bfs_box());
    151         cout<<bfs_box()<<endl<<endl;
    152     }
    153     return 0;
    154 }
  • 相关阅读:
    什么叫继承?
    两类交换元素使序列有序 求最少交换次数的题
    如何理解汉诺塔
    求给出第 K个 N位二进制数,该二进制数不得有相邻的“1”
    7/26 CSU-ACM2018暑期训练3-递归&递推-选讲
    平面分割
    递推算法之平面分割问题总结
    UTC时间
    7/25 CSU-ACM2018暑假集训比赛1
    洛谷 P1824 进击的奶牛【二分答案/类似青蛙过河】
  • 原文地址:https://www.cnblogs.com/Missa/p/2714435.html
Copyright © 2011-2022 走看看