USACO 玉米田迷宫 Corn Maze

来源:互联网 发布:剑雨江湖源码 编辑:程序博客网 时间:2024/04/28 06:57

移步到新Blog查看图片 (此Blog已废弃,图片已失效)




这题是一个大坑。

首先我们想到了BFS,这个题就是一个简单到不能再简单的Maze加上传送门就是了。

但是有一点是传送门不费时啊!!什么鬼。所以我们要先判传送门

为什么呢?我记得有一组测试数据包括了这种情况


这不清真

另外,好像还有一个点是全都是传送门的情况。


判传送门(并不是判队首元素位于传送门,而是队首坐标移动之后),传送过去之后耗时不加,队列保存传送后的位置,这样就不会产生无限传送死循环的问题。

但是关于情况2怎么办?我们利用BFS的性质,把传送门(传过去之后)打上标记,然后就不用他了。(每一次用都是最早用他)

传送门I hate you


读入的时候记录传送门的相对坐标,像这样:

scanf("%s",&mapx[i]);for (int j=0;j<m;j++){if (mapx[i][j]=='='){ex=i;ey=j;}else if (mapx[i][j]=='@'){sx=i;sy=j;}else if (mapx[i][j]>='A' && mapx[i][j]<='Z'){if (toit[mapx[i][j]-65][0][0]==-1){toit[mapx[i][j]-65][0][0]=i; toit[mapx[i][j]-65][0][1]=j;}else toit[mapx[i][j]-65][1][0]=i; toit[mapx[i][j]-65][1][1]=j;}}
之后碰到传送门直接查表。,顺便记下起点sxsy和重点exey

#include<cstdio>#include<iostream>#include<cstring>#include<string>#include<queue>#include<map>#include<algorithm>using namespace std;queue<int>quex,quey;int cachex,cachey;char mapx[400][400]={0};int sx,sy,ex,ey,n,m;int head=0,tail=1;int timex[100000]={0},toit[50][2][2];bool checked[400][400]={false};int wayx[4]={-1,0,1,0},wayy[4]={0,1,0,-1};int main(){memset(toit,-1,sizeof(toit));scanf("%d%d",&n,&m);for (int i=0;i<n;i++){scanf("%s",&mapx[i]);for (int j=0;j<m;j++){if (mapx[i][j]=='=') { ex=i;ey=j;}else if (mapx[i][j]=='@') { sx=i;sy=j;}else if (mapx[i][j]>='A' && mapx[i][j]<='Z'){if (toit[mapx[i][j]-65][0][0]==-1) toit[mapx[i][j]-65][0][0]=i; toit[mapx[i][j]-65][0][1]=j;else toit[mapx[i][j]-65][1][0]=i; toit[mapx[i][j]-65][1][1]=j;}}}quex.push(sx); quey.push(sy);timex[1]=0;while (quex.size()>0){head++;cachex=quex.front(); cachey=quey.front();if (mapx[cachex][cachey]=='='){printf("%d\n",timex[head]);return 0;}for (int i=0;i<=3;i++)if (cachex+wayx[i]>=0 && cachex+wayx[i]<n && cachey+wayy[i]>=0 && cachey+wayy[i]<m){if (mapx[cachex+wayx[i]][cachey+wayy[i]]>='A' && mapx[cachex+wayx[i]][cachey+wayy[i]]<='Z' && checked[cachex+wayx[i]][cachey+wayy[i]]==false){if (cachex+wayx[i]==toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][0][0] && cachey+wayy[i]==toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][0][1]){tail++;quex.push(toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][1][0]); quey.push(toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][1][1]);timex[tail]=timex[head]+1;checked[cachex+wayx[i]][cachey+wayy[i]]=true;//cout<<"A  "<<"X= "<<toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][1][0]<<" Y= "<<toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][1][1]<<" Timex= "<<timex[tail]<<" X= "<<cachex<<" Y= "<<cachey<<endl;}else {tail++;quex.push(toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][0][0]); quey.push(toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][0][1]);timex[tail]=timex[head]+1;checked[cachex+wayx[i]][cachey+wayy[i]]=true;//cout<<"B  "<<"X= "<<toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][0][0]<<" Y= "<<toit[mapx[cachex+wayx[i]][cachey+wayy[i]]-65][0][1]<<" Timex= "<<timex[tail]<<" X= "<<cachex<<" Y= "<<cachey<<endl;}}else if (mapx[cachex+wayx[i]][cachey+wayy[i]]!='#' && checked[cachex+wayx[i]][cachey+wayy[i]]==false){tail++;quex.push(cachex+wayx[i]); quey.push(cachey+wayy[i]);timex[tail]=timex[head]+1;checked[cachex+wayx[i]][cachey+wayy[i]]=true;//cout<<"X= "<<cachex+wayx[i]<<" Y= "<<cachey+wayy[i]<<" Timex= "<<timex[tail]<<endl;}}quex.pop(); quey.pop();}return 0; }


其实这个题处理好了传送门,你会发现,其实不难……(输出调试大法好)

记得用checked数组标记已经访问的点和传送门,要不无限使用传送门


原创粉丝点击