码迷,mamicode.com
首页 > 其他好文 > 详细

搜索进阶题

时间:2014-11-02 22:17:32      阅读:293      评论:0      收藏:0      [点我收藏+]

标签:style   blog   http   io   color   ar   os   for   sp   

 

1.http://acm.hdu.edu.cn/showproblem.php?pid=1254

分析:由于箱子每次都只能推,而不能拉,所以我们知道,每次往方向 i 推的时候,人必然会站在一个确切的位置 p 。所以我们在每次推箱子的时候先bfs求出人是否可以到达 p 位置。若可以到达 p ,则往 p 的对面的推动一格,否则判断下一个方向。直到推到目标位置为止。然后我们得到下面的代码:

bubuko.com,布布扣
  1 //First Edit Time:    2014-11-02 17:06
  2 //Last Edit Time:    2014-11-02 18:20
  3 #include <cstdio>
  4 #include <cstring>
  5 #include <queue>
  6 using namespace std;
  7 
  8 struct Pos
  9 {
 10     int bx, by;
 11     int px, py;
 12     int step;
 13 }Box, Person;
 14 
 15 int map[10][10], n, m;
 16 bool used[10][10][10][10];
 17 int dir[4][2]={{1,0},{-1,0},{0,1},{0,-1}};
 18 bool visited[10][10];
 19 
 20 bool Judge_Person (Pos a)
 21 {
 22     if(a.px<0 || a.px>m-1 || a.py<0 || a.py>n-1 || visited[a.px][a.py]
 23             || map[a.px][a.py]==1 || (a.px==Box.bx && a.py==Box.by))
 24         return false;
 25     return true;
 26 }
 27 
 28 bool Judge_Box (Pos a)
 29 {
 30     if(a.bx<0 || a.bx>m-1 || a.by<0 || a.by>n-1 || used[a.bx][a.by][Person.px][Person.py] || map[a.bx][a.by]==1)
 31         return false;
 32     return true;
 33 }
 34 
 35 Pos Find_p (Pos a, int i)
 36 {
 37     Pos P = a;
 38     if (i==0)
 39     {
 40         P.px = a.bx + dir[1][0];
 41         P.py = a.by + dir[1][1];
 42     }
 43     else if (i==1)
 44     {
 45         P.px = a.bx + dir[0][0];
 46         P.py = a.by + dir[0][1];
 47     }
 48     else if (i==2)
 49     {
 50         P.px = a.bx + dir[3][0];
 51         P.py = a.by + dir[3][1];
 52     }
 53     else if (i==3)
 54     {
 55         P.px = a.bx + dir[2][0];
 56         P.py = a.by + dir[2][1];
 57     }
 58     return P;
 59 }
 60 
 61 //
 62 bool bfs_person (Pos a)
 63 {
 64     memset (visited, 0, sizeof visited);
 65     if (!Judge_Person (a)) return false;
 66 
 67     Pos Pre, Cur;
 68     queue <Pos> Q;
 69     visited[Person.px][Person.py] = true;
 70 
 71     Q.push (Person);
 72     while (!Q.empty())
 73     {
 74         Pre = Q.front();
 75         Q.pop();
 76         for (int i=0; i<4; i++)
 77         {
 78             Cur.px = Pre.px + dir[i][0];
 79             Cur.py = Pre.py + dir[i][1];
 80             if (Judge_Person (Cur))
 81             {
 82                 visited[Cur.px][Cur.py] = true;
 83                 if (Cur.px==a.px && Cur.py==a.py)
 84                     return true;
 85                 Q.push (Cur);
 86             }
 87         }
 88     }
 89     return false;
 90 }
 91 
 92 int bfs_box ()
 93 {
 94     Pos Pre, Cur, P;
 95     queue <Pos> Q;
 96     memset (used, 0, sizeof used);
 97 
 98     used[Box.bx][Box.by][Person.px][Person.py] = true;
 99     Q.push (Box);
100     while (!Q.empty ())
101     {
102         Pre = Q.front ();
103         Q.pop();
104         for (int i=0; i<4; i++)
105         {
106             Box = Pre;
107 
108             //找到推箱子的位置
109             P = Find_p (Pre, i);
110             
111             if (bfs_person (P))
112             {
113                 Cur = Pre;
114                 Person = P;
115                 Cur.bx += dir[i][0];
116                 Cur.by += dir[i][1];
117                 Cur.step += 1;
118                 if (Judge_Box (Cur))
119                 {
120                     used[Cur.bx][Cur.by][Person.px][Person.py] = true;
121                     if (map[Cur.bx][Cur.by]==3)
122                         return Cur.step;
123                     Q.push (Cur);
124                 }
125             }
126         }
127     }
128     return -1;
129 }
130 
131 int main ()
132 {
133     int t;
134     freopen ("test.in","r",stdin);
135     scanf ("%d",&t);
136     while (t--)
137     {
138         scanf ("%d%d",&m, &n);
139         for (int i=0; i<m; i++)
140             for (int j=0; j<n; j++)
141             {
142                 scanf ("%d",map[i]+j);
143                 if (map[i][j]==2)
144                     Box.bx=i, Box.by=j, Box.step=0;
145                 else if (map[i][j]==4)
146                     Person.px = i,Person.py = j;
147             }
148         int ans = bfs_box ();
149         printf ("%d\n",ans);
150     }
151     return 0;
152 }
View Code

  然后我就这样一直WA到死。后来问了学长才知道,其实我没有考虑到另一种情况:

1
5 3
0 0 0
0 0 0
0 2 0
1 4 1
1 3 1

在上面这种情况下,以上代码得到的答案是-1,因为上面的程序一开始就访问了他本应该去的位置 p ,导致最后要用到 p 的时候得到 p 不可到达的错误信息而是答案出错。

改正之后的代码:

bubuko.com,布布扣
  1 //First Edit Time:    2014-11-02 17:06
  2 //Last Edit Time:    2014-11-02 18:20
  3 #include <cstdio>
  4 #include <cstring>
  5 #include <queue>
  6 using namespace std;
  7 
  8 struct Pos
  9 {
 10     int bx, by;
 11     int px, py;
 12     int step;
 13 }Box, Person;
 14 
 15 int map[10][10], n, m;
 16 bool used[10][10][10][10];
 17 int dir[4][2]={{1,0},{-1,0},{0,1},{0,-1}};
 18 bool visited[10][10];
 19 
 20 bool Judge_Person (Pos a)
 21 {
 22     if(a.px<0 || a.px>m-1 || a.py<0 || a.py>n-1 || visited[a.px][a.py]
 23             || map[a.px][a.py]==1 || (a.px==Box.bx && a.py==Box.by))
 24         return false;
 25     return true;
 26 }
 27 
 28 bool Judge_Box (Pos a)
 29 {
 30     if(a.bx<0 || a.bx>m-1 || a.by<0 || a.by>n-1 || used[a.bx][a.by][Person.px][Person.py] || map[a.bx][a.by]==1)
 31         return false;
 32     return true;
 33 }
 34 
 35 Pos Find_p (Pos a, int i)
 36 {
 37     Pos P = a;
 38     if (i==0)
 39     {
 40         P.px = a.bx + dir[1][0];
 41         P.py = a.by + dir[1][1];
 42     }
 43     else if (i==1)
 44     {
 45         P.px = a.bx + dir[0][0];
 46         P.py = a.by + dir[0][1];
 47     }
 48     else if (i==2)
 49     {
 50         P.px = a.bx + dir[3][0];
 51         P.py = a.by + dir[3][1];
 52     }
 53     else if (i==3)
 54     {
 55         P.px = a.bx + dir[2][0];
 56         P.py = a.by + dir[2][1];
 57     }
 58     return P;
 59 }
 60 
 61 //
 62 bool bfs_person (Pos a)
 63 {
 64     memset (visited, 0, sizeof visited);
 65     if (!Judge_Person (a)) return false;
 66     if (a.px==Person.px && a.py==Person.py)  //改正之处。就是把那种情况特判了一下;
 67         return true;
 68     Pos Pre, Cur;
 69     queue <Pos> Q;
 70     visited[Person.px][Person.py] = true;
 71 
 72     Q.push (Person);
 73     while (!Q.empty())
 74     {
 75         Pre = Q.front();
 76         Q.pop();
 77         for (int i=0; i<4; i++)
 78         {
 79             Cur.px = Pre.px + dir[i][0];
 80             Cur.py = Pre.py + dir[i][1];
 81             if (Judge_Person (Cur))
 82             {
 83                 visited[Cur.px][Cur.py] = true;
 84                 if (Cur.px==a.px && Cur.py==a.py)
 85                     return true;
 86                 Q.push (Cur);
 87             }
 88         }
 89     }
 90     return false;
 91 }
 92 
 93 int bfs_box ()
 94 {
 95     Pos Pre, Cur, P;
 96     queue <Pos> Q;
 97     memset (used, 0, sizeof used);
 98 
 99     used[Box.bx][Box.by][Person.px][Person.py] = true;
100     Q.push (Box);
101     while (!Q.empty ())
102     {
103         Pre = Q.front ();
104         Q.pop();
105     //  printf ("Box:(%d, %d) ---- %d\n",Pre.bx+1, Pre.by+1, Pre.step);
106         for (int i=0; i<4; i++)
107         {
108             Box = Pre;
109 
110             //找到推箱子的位置
111             P = Find_p (Pre, i);
112         //    printf ("Person:(%d,%d)\n",P.px+1,P.py+1);
113             if (bfs_person (P))
114             {
115                 Cur = Pre;
116                 Person = P;
117                 Cur.bx += dir[i][0];
118                 Cur.by += dir[i][1];
119                 Cur.step += 1;
120     //        printf ("Goto:(%d, %d)\n",Cur.bx+1, Cur.by+1);
121                 if (Judge_Box (Cur))
122                 {
123                     used[Cur.bx][Cur.by][Person.px][Person.py] = true;
124                     if (map[Cur.bx][Cur.by]==3)
125                         return Cur.step;
126                     Q.push (Cur);
127                 }
128             }
129         }
130     }
131     return -1;
132 }
133 
134 int main ()
135 {
136     int t;
137     freopen ("test.in","r",stdin);
138     scanf ("%d",&t);
139     while (t--)
140     {
141         scanf ("%d%d",&m, &n);
142         for (int i=0; i<m; i++)
143             for (int j=0; j<n; j++)
144             {
145                 scanf ("%d",map[i]+j);
146                 if (map[i][j]==2)
147                     Box.bx=i, Box.by=j, Box.step=0;
148                 else if (map[i][j]==4)
149                     Person.px = i,Person.py = j;
150             }
151         int ans = bfs_box ();
152         printf ("%d\n",ans);
153     }
154     return 0;
155 }
View Code

 

搜索进阶题

标签:style   blog   http   io   color   ar   os   for   sp   

原文地址:http://www.cnblogs.com/khan724/p/4069932.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!