noip2013 华容道

Posted A_LEAF

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了noip2013 华容道相关的知识,希望对你有一定的参考价值。

solution

 


 

暴力(70):

定义f[x1][y1][x2][y2]为空格在(x1,y1),目标棋子在(x2,y2),时的最小步数

之后bfs就行

正解:

也是bfs

预处理出来数组 g[x][y][k][kk]  1<=k,kk<=4

意义是 当前棋子在(x,y)白棋子在k方向(上下左右),想要走到kk方向的最小步数

 

之后对于每次询问

首先把白格子挪到目标旗子周围,之后把目标棋子挪到目标位置,bfs利用g[][][][]数组

 

技术分享
  1 #include<cstdio>
  2 #include<cstring>
  3 #include<iostream>
  4 #include<queue>
  5 #define mem(a,b) memset(a,b,sizeof(a))
  6 using namespace std;
  7 const int DUI=20000006;
  8 const int INF=0x7fffffff;
  9 
 10 inline int minn(int a,int b){return a<b?a:b;}
 11 
 12 struct Queue
 13 {
 14     int x,y;
 15 };
 16 
 17 queue<Queue> q;
 18 int n,m,Q,qqq;
 19 int bx[6]={0,-1,1,0,0,0};
 20 int by[6]={0,0,0,-1,1,0};// 1 上 2 下 3 左 4 右 
 21 int f[36][36][6],ha[6],flag[36][36],vis[36][36][6];
 22 int a[36][36],g[36][36][6][6],d[36][36];
 23 int whx,why,sx,sy,tx,ty;
 24 
 25 void out11();
 26 
 27 void chu()
 28 {
 29     mem(g,60);
 30     qqq=g[0][0][0][0];
 31     Queue now;
 32     int x,y;
 33     for(int i=1;i<=n;++i)
 34       for(int j=1;j<=m;++j)
 35       {
 36           if(a[i][j]==0)
 37             continue;
 38         for(int bai=1;bai<=4;++bai)
 39         {//printf("saafsffas\n");
 40                 if( (i+bx[bai]<1) || (i+bx[bai]>n) || (j+by[bai]<1) || (j+by[bai]>m) || (a[i+bx[bai]][j+by[bai]]==0) )
 41                   continue;
 42           for(int tt=1;tt<=4;++tt)
 43           {
 44                     if( (i+bx[tt]<1) || (i+bx[tt]>n) || (j+by[tt]<1) || (j+by[tt]>m) || (a[i+bx[tt]][j+by[tt]]==0) )
 45                       continue;
 46                     //printf("i=%d j=%d\n",i,j);
 47                     if(bai==tt)
 48                     {
 49                         g[i][j][bai][tt]=0;
 50                       continue;
 51                     }
 52                     
 53                     
 54                     
 55                     while(!q.empty())q.pop();
 56                     mem(d,60);mem(flag,0);
 57                     sx=i+bx[bai];sy=j+by[bai];
 58                     tx=i+bx[tt];ty=j+by[tt];
 59                     d[sx][sy]=0;flag[sx][sy]=1;
 60                     q.push((Queue){sx,sy});
 61                     while(!q.empty())
 62                     {
 63             
 64                         now=q.front();q.pop();
 65                         x=now.x;y=now.y;flag[x][y]=0;
 66                         //if(x==tx&&y==ty)
 67                         //  break;
 68                         
 69                         for(int k=1;k<=4;++k)
 70                         {
 71                             if(x+bx[k]<1||x+bx[k]>n||y+by[k]<1||y+by[k]>m||a[x+bx[k]][y+by[k]]==0|| (x+bx[k]==i&&y+by[k]==j) )
 72                               continue;
 73                             //printf("sdasdasd\n");
 74                             if(d[x+bx[k]][y+by[k]]>d[x][y]+1)
 75                             {
 76                                 d[x+bx[k]][y+by[k]]=d[x][y]+1;
 77                                 if(!flag[x+bx[k]][y+by[k]])
 78                                 {
 79                                     q.push((Queue){x+bx[k],y+by[k]});
 80                                     flag[x+bx[k]][y+by[k]]=1;
 81                                 }
 82                             }
 83                         }
 84                     }
 85                     
 86                     //g[i][j][bai][tt]=d[tx][ty]+1;
 87                     g[i][j][bai][tt]=d[tx][ty];
 88                     
 89                     //out11();
 90                     
 91                     //printf("i=%d j=%d k=%d l=%d g[][][][]=%d\n",i,j,bai,tt,g[i][j][bai][tt]);
 92                 }
 93             }
 94         }
 95 }// yes
 96 
 97 int bfs1()
 98 {
 99     Queue now;
100     int x,y;
101     mem(d,60);
102     while(!q.empty())q.pop();
103     mem(flag,0);
104     d[whx][why]=0;flag[whx][why]=1;
105     q.push((Queue){whx,why});
106     while(!q.empty())
107     {
108         now=q.front();q.pop();
109         x=now.x;y=now.y;flag[x][y]=0;
110         for(int k=1;k<=4;++k)
111         {
112             if(x+bx[k]<1||x+bx[k]>n||y+by[k]<1||y+by[k]>m||a[x+bx[k]][y+by[k]]==0|| (x+bx[k]==sx&&y+by[k]==sy) )
113               continue;
114             if(d[x+bx[k]][y+by[k]]>d[x][y]+1)
115             {
116                 d[x+bx[k]][y+by[k]]=d[x][y]+1;
117                 if(!flag[x+bx[k]][y+by[k]])
118                 {
119                     q.push((Queue){x+bx[k],y+by[k]});
120                     flag[x+bx[k]][y+by[k]]=1;
121                 }
122             }
123         }
124     }
125     
126     for(int i=1;i<=4;++i)
127       if(d[sx+bx[i]][sy+by[i]]<qqq)
128         return 1;
129     return 0;
130 }
131 
132 struct son
133 {
134     int x,y,k;
135 };
136 queue<son> dui;
137 
138 int bfs2()
139 {
140     son now;
141     int x,y,nowk;
142     mem(f,60);mem(vis,0);
143     for(int i=1;i<=4;++i)
144     {
145       if(sx+bx[i]<1||sx+bx[i]>n||sy+by[i]<1||sy+by[i]>m||a[sx+bx[i]][sy+by[i]]==0||d[sx+bx[i]][sy+by[i]]==qqq)
146         continue;
147       f[sx][sy][i]=d[sx+bx[i]][sy+by[i]];
148       vis[sx][sy][i]=1;
149       //printf("ssdad=%d\n",d[sx+bx[i]][sy+by[i]]);
150       dui.push((son){sx,sy,i});
151     }
152     
153     //out11();
154     
155     while(!dui.empty())
156     {
157         now=dui.front();dui.pop();
158         x=now.x;y=now.y;nowk=now.k;
159         vis[x][y][nowk]=0;
160         
161         for(int i=1;i<=4;++i)
162         {
163             if(x+bx[i]<1|| (x+bx[i]>n) || (y+by[i]<1) || (y+by[i]>m) || (a[x+bx[i]][y+by[i]]==0) )
164               continue;
165             //printf("hhahahahahha\n");
166             int temp1=f[x+bx[i]][y+by[i]][ha[i]];
167             int temp2=f[x][y][nowk]+1+g[x][y][nowk][i];
168             //printf("%d %d\n",temp1,temp2);
169             if(temp1>temp2)
170             {
171                 
172                 f[x+bx[i]][y+by[i]][ha[i]]=f[x][y][nowk]+1+g[x][y][nowk][i];
173                 if(!vis[x+bx[i]][y+by[i]][ha[i]])//////????????
174                 {
175                     dui.push((son){x+bx[i],y+by[i],ha[i]});
176                     vis[x+bx[i]][y+by[i]][ha[i]]=1;
177                 }
178             }
179         }
180     }
181     
182     //out11();
183     
184     int ans=INF;
185     for(int i=1;i<=4;++i)
186       ans=minn(ans,f[tx][ty][i]);
187     return ans;
188 }
189 
190 void out11()
191 {
192     printf("\n");
193     for(int k=1;k<=4;++k)
194     {
195     for(int i=1;i<=n;++i)
196     {
197       for(int j=1;j<=m;++j)
198         printf("%d ",f[i][j][k]);
199       printf("\n");
200     }
201     printf("\n");
202   }
203   
204     /*for(int i=1;i<=n;++i)
205     {
206     for(int j=1;j<=m;++j)
207       printf("%d ",d[i][j]);
208     printf("\n");
209   }*/
210     /*for(int i=1;i<=n;++i)
211       for(int j=1;j<=m;++j)
212         for(int k=1;k<=4;++k)
213           for(int l=1;l<=4;++l)
214             if(g[i][j][k][l]!=qqq)
215               printf("i=%d j=%d k=%d l=%d g[][][][]=%d\n",i,j,k,l,g[i][j][k][l]);*/
216     printf("\n");
217 }
218 
219 int main(){
220     
221     //freopen("1.txt","r",stdin);
222     
223     scanf("%d%d%d",&n,&m,&Q);
224     for(int i=1;i<=n;++i)
225       for(int j=1;j<=m;++j)
226         scanf("%d",&a[i][j]);
227     chu();
228     ha[1]=2;ha[2]=1;ha[3]=4;ha[4]=3;
229     
230     //out11();
231     
232     while(Q--)
233     {
234         scanf("%d%d%d%d%d%d",&whx,&why,&sx,&sy,&tx,&ty);
235         if(sx==tx&&sy==ty)
236         {
237             printf("0\n");
238             continue;
239         }
240         if(bfs1()==0)
241         {
242             printf("-1\n");
243             continue;
244         }
245         int temp=bfs2();
246         if(temp>=qqq)
247         {
248             printf("-1\n");
249             continue;
250         }
251         printf("%d\n",temp);
252     }
253     
254     //while(1);
255     return 0;
256 }
code

 

以上是关于noip2013 华容道的主要内容,如果未能解决你的问题,请参考以下文章

NOIP2013华容道

[Noip2013]华容道

NOIP2013 华容道

[NOIP2013]华容道

CodeVS 3290NOIP 2013华容道

NOIP2013 华容道