POJ 3083 -- Children of the Candy Corn(DFS+BFS)TLE

POJ 3083 -- Children of the Candy Corn(DFS+BFS)

题意:

给定一个迷宫,S是起点,E是终点,#是墙不可走,.可以走

1)先输出左转优先时,从S到E的步数

2)再输出右转优先时,从S到E的步数

3)最后输出S到E的最短步数

解题思路:

前两问DFS,转向只要控制一下旋转方向就可以

首先设置前进方向对应的数字

向上——N——0

向右——E——1

向下——S——2

向左——W——3

比如说右转优先,即为向右,向前,向左,向后,即逆时针方向for(int i=1;i>=-2;i--)

左转优先,即为向左,向前,向右,向后,即顺时针方向for(int i=-1;i<=3;i++)

第三问最短路,BFS

普通递归(TLE)

  1 #include<iostream>
  2 #include<cstring>
  3 #include<queue>
  4 #include<cstdio>
  5 using namespace std;
  6 int r,c;///行r,列c
  7 int r0,c0,r3,c3;///r0,c0用来标记入口,r3,c3用来标记出口
  8 const char *dirs = "NESW";
  9 const int maxn = 41;
 10 char square[maxn][maxn];
 11 const int dr[] = {-1,0,1,0};
 12 const int dc[] = { 0,1,0,-1};
 13 struct node{
 14 int row,col,deep;
 15 int dir;///0123对应NESW
 16 node(int row=0,int col=0,int dir=0,int deep=0):row(row),col(col),dir(dir),deep(deep){}
 17 };
 18 bool inside(int xx,int yy)
 19 {
 20     return xx>=1 && xx<=r && yy>=1 && yy<=c;
 21 }
 22
 23 bool flag1;
 24 int step1;
 25 void dfs1(node *way,int x,int y,int d,int step)
 26 {///左转优先
 27     way[step].row = x;
 28     way[step].col = y;
 29     way[step].dir = d;
 30     if(x==r3 && y==c3)///走到出口
 31     {
 32         step1 = step;
 33         flag1 = true;
 34         return;
 35     }
 36     for(int i=-1;i<=3;i++)
 37     {
 38         int tempDir = (way[step].dir + 4 + i)%4;///进行旋转
 39         int xx = way[step].row + dr[tempDir];
 40         int yy = way[step].col + dc[tempDir];
 41         if(inside(xx,yy) && square[xx][yy]!=‘#‘)
 42         {///没有出界,可以行走
 43             dfs1(way,xx,yy,tempDir,step+1);
 44         }
 45         if(flag1)
 46             return;
 47     }
 48     return;
 49 }
 50
 51 int step2;bool flag2;
 52 void dfs2(node *way,int x,int y,int d,int step)
 53 {///右转优先
 54     way[step].row = x;
 55     way[step].col = y;
 56     way[step].dir = d;
 57     if(x==r3 && y==c3)///走到出口
 58     {
 59         step2 = step;
 60         flag2 = true;
 61         return;
 62     }
 63     for(int i=1;i>=-2;i--)
 64     {
 65         int tempDir = (way[step].dir + 4 + i)%4;///进行旋转
 66         int xx = way[step].row + dr[tempDir];
 67         int yy = way[step].col + dc[tempDir];
 68         if(inside(xx,yy) && square[xx][yy]!=‘#‘)
 69         {///没有出界,可以行走
 70             dfs2(way,xx,yy,tempDir,step+1);
 71         }
 72         if(flag2)
 73             return;
 74     }
 75     return;
 76 }
 77 node d[maxn][maxn][4];
 78
 79 void bfs(int x,int y,int d)
 80 {
 81     queue<node> q;
 82     node u(x,y,d,1);///入口结点
 83     q.push(u);
 84     while(!q.empty())
 85     {
 86         node u = q.front();q.pop();
 87         if(u.row == r3 && u.col == c3)
 88         {
 89             cout<<u.deep<<endl;
 90             return;
 91         }
 92         for(int i=0;i<=3;i++)
 93         {
 94             int tempDir = (u.dir +i)%4;///进行旋转
 95             int xx = u.row + dr[tempDir];
 96             int yy = u.col + dc[tempDir];
 97             if(inside(xx,yy) && square[xx][yy]!=‘#‘)
 98             {///没有出界,可以行走
 99                 node v(xx,yy,tempDir,u.deep+1);
100                 q.push(v);
101             }
102         }
103     }
104 }
105
106 int startDir()
107 {///计算从入口进入之后的方向
108     if(r0 == 1) return 2;
109     else if(r0 == r) return 0;
110     else if(c0 == 1) return 1;
111     else return 3;
112 }
113 int main()
114 {
115     int n;
116     cin>>n;
117     while(n--)
118     {
119         cin>>c>>r;///输入为先输入列数,在输入行数
120         char temp;
121         for(int i=1;i<=r;i++)
122             for(int j=1;j<=c;j++)
123             {
124                 temp = getchar();
125                 while(temp == ‘\n‘) temp = getchar();
126                 square[i][j] = temp;
127                 if(temp == ‘S‘){r0 = i;c0 = j;}
128                 if(temp == ‘E‘){r3 = i;c3 = j;}
129             }
130         node *way = new node[maxn*maxn];
131         ///求解左转优先
132         flag1 = false;step1 = 1;
133         int startdir = startDir();
134         dfs1(way,r0,c0,startdir,1);
135         if(flag1) cout<<step1<<" ";
136         ///求解右转优先
137         flag2 = false;step2 = 1;
138         dfs2(way,r0,c0,startdir,1);
139         if(flag2) cout<<step2<<" ";
140         ///求解最短路径
141         bfs(r0,c0,startdir);
142     }
143     return 0;
144 }

尾递归形式+精简代码(依旧TLE):

  1 #include<iostream>
  2 #include<cstring>
  3 #include<queue>
  4 #include<cstdio>
  5 using namespace std;
  6 int r,c;///行r,列c
  7 int r0,c0,r3,c3;///r0,c0用来标记入口,r3,c3用来标记出口
  8
  9 const int maxn = 41;
 10 char square[maxn][maxn];
 11 const int dr[] = {-1,0,1,0};
 12 const int dc[] = { 0,1,0,-1};
 13
 14 struct node{
 15 int row,col,deep;
 16 int dir;///0123对应NESW
 17 node(int row=0,int col=0,int dir=0,int deep=0):row(row),col(col),dir(dir),deep(deep){}
 18 };
 19
 20 int dfs12(int x,int y,int d)
 21 {///左转优先
 22
 23     if(square[x][y] == ‘E‘)
 24         return 1;
 25     int tempDir,xx,yy;
 26     for(int i=-1;i<=3;i++)
 27     {
 28         tempDir = (d + 4 + i)%4;///进行旋转
 29         xx = x + dr[tempDir];
 30         yy = y + dc[tempDir];
 31         if(square[xx][yy]==‘.‘ || square[xx][yy]==‘E‘ ||square[xx][yy]==‘S‘)
 32         {///没有出界,可以行走
 33             break;
 34         }
 35     }
 36     return dfs12(xx,yy,tempDir)+1;
 37 }
 38 int dfs22(int x,int y,int d)
 39 {///you转优先
 40     if(square[x][y] == ‘E‘)
 41         return 1;
 42     int tempDir,xx,yy;
 43
 44     for(int i=1;i>=-2;i--)
 45     {
 46         tempDir = (d + 4 + i)%4;///进行旋转
 47         xx = x + dr[tempDir];
 48         yy = y + dc[tempDir];
 49         if(square[xx][yy]==‘.‘ || square[xx][yy]==‘E‘ ||square[xx][yy]==‘S‘)
 50         {///没有出界,可以行走
 51             break;
 52         }
 53     }
 54     return dfs22(xx,yy,tempDir)+1;
 55 }
 56
 57 node d[maxn][maxn][4];
 58
 59 void bfs(int x,int y,int d)
 60 {
 61     queue<node> q;
 62     node u(x,y,d,1);///入口结点
 63     q.push(u);
 64     while(!q.empty())
 65     {
 66         node u = q.front();q.pop();
 67         if(u.row == r3 && u.col == c3)
 68         {
 69             cout<<u.deep<<endl;
 70             return;
 71         }
 72         for(int i=0;i<=3;i++)
 73         {
 74             int tempDir = (u.dir +i)%4;///进行旋转
 75             int xx = u.row + dr[tempDir];
 76             int yy = u.col + dc[tempDir];
 77             if(square[xx][yy]==‘.‘ || square[xx][yy]==‘E‘ ||square[xx][yy]==‘S‘)
 78             {///没有出界,可以行走
 79                 node v(xx,yy,tempDir,u.deep+1);
 80                 q.push(v);
 81             }
 82         }
 83     }
 84 }
 85
 86 int startDir()
 87 {///计算从入口进入之后的方向
 88     if(r0 == 1) return 2;
 89     else if(r0 == r) return 0;
 90     else if(c0 == 1) return 1;
 91     else return 3;
 92 }
 93 int main()
 94 {
 95     int n;
 96     cin>>n;
 97     while(n--)
 98     {
 99         cin>>c>>r;///输入为先输入列数,在输入行数
100         char temp;
101         for(int i=1;i<=r;i++)
102             for(int j=1;j<=c;j++)
103             {
104                 temp = getchar();
105                 while(temp == ‘\n‘) temp = getchar();
106                 square[i][j] = temp;
107                 if(temp == ‘S‘){r0 = i;c0 = j;}
108                 if(temp == ‘E‘){r3 = i;c3 = j;}
109             }
110         ///求解左转优先
111         int startdir = startDir();
112         cout<<dfs12(r0,c0,startdir)<<" ";
113         ///求解右转优先
114         cout<<dfs22(r0,c0,startdir)<<" ";
115         ///求解最短路径
116         bfs(r0,c0,startdir);
117     }
118     return 0;
119 }

暂存问题……

原文地址:https://www.cnblogs.com/yxh-amysear/p/8453849.html

时间: 2024-12-21 00:13:13

POJ 3083 -- Children of the Candy Corn(DFS+BFS)TLE的相关文章

POJ 3083 Children of the Candy Corn (DFS+BFS)

题目链接:http://poj.org/problem?id=3083 题目大意:给你一个迷宫,S是起点,E是终点,#是墙,.是路,S.E在迷宫的边界,并且有唯一解:求优先左转S到E的步数,优先右转S到E的步数,以及S到E的最短步数. 题解: 1.本题的难点在于左转优先以及右转优先,下一步的方向取决于当前位置的方向,用DFS不断的按优先方向遍历一遍迷宫即可:我定义如图:   前(0)   左(1) 当前位置方向(dir) 右(3)   后(2)   以左转优先为例,便利迷宫的方向依次为:左.前.

POJ 3083:Children of the Candy Corn(DFS+BFS)

Children of the Candy Corn Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 9311 Accepted: 4039 Description The cornfield maze is a popular Halloween treat. Visitors are shown the entrance and must wander through the maze facing zombies, ch

POJ 3083 Children of the Candy Corn(顺时针DFS+逆时针DFS+BFS)

题目链接:POJ 3083 Children of the Candy Corn [题意]给出一个迷宫,不超过40*40,'#'代表墙,'.'代表能走,'S'是起点,'E'是终点.分别求出从起点一直沿左走,一直沿右走,走到终点所需要的步数.以及走出迷宫的最小步数. [思路]首先最小步数很简单,一个普通BFS搞定,这道题重点是一直向左走和一直向右走的DFS的方向问题,方向还和游客当时朝向有关.开始一直认为是每次都向左(右)转,直到可以走,然后就一直不对,在google了之后才知道向左走要遵循左上右

POJ 3083 Children of the Candy Corn(搜索)

Children of the Candy Corn Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 10975   Accepted: 4731 Description The cornfield maze is a popular Halloween treat. Visitors are shown the entrance and must wander through the maze facing zombie

POJ 3083 Children of the Candy Corn

Children of the Candy Corn Time Limit: 1000ms Memory Limit: 65536KB This problem will be judged on PKU. Original ID: 308364-bit integer IO format: %lld      Java class name: Main The cornfield maze is a popular Halloween treat. Visitors are shown the

poj 3083 Children of the Candy Corn(bfs+dfs)

Children of the Candy Corn Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 10739   Accepted: 4626 Description The cornfield maze is a popular Halloween treat. Visitors are shown the entrance and must wander through the maze facing zombie

POJ 3083 Children of the Candy Corn (DFS + BFS + 模拟)

题目链接:http://poj.org/problem?id=3083 题意: 这里有一个w * h的迷宫,给你入口和出口,让你分别求以下三种情况时,到达出口的步数(总步数包括入口和出口): 第一种:当你需要选择下一个位置时,总是需要这么考虑:如果当前的左方能走,那么就走左方;否则考虑前方是否能走,如果能走,那么就选前方;否则考虑右方是否能走,如果可以,就走右方.如果不能就返回上一个位置,即当前位置的后方.总结下来选择道路的优先顺序为(以当前所处方位为准) 左 -> 上(前) -> 右 -&g

搜索模板(DFS/BFS)

DFS int b[4][2] = {-1,0,0,1,1,0,0,-1}; int DFS( pair<int,int> x ) { int res=0; visited[x.first][x.second]=1; for( int i=0;i<4;i++ ){ pair<int,int> tmp; tmp.first=x.first+b[i][0]; tmp.second=x.second+b[i][1]; if( check(tmp) ) { visited[tmp.f

POJ-3083 Children of the Candy Corn (BFS+DFS)

Description The cornfield maze is a popular Halloween treat. Visitors are shown the entrance and must wander through the maze facing zombies, chainsaw-wielding psychopaths, hippies, and other terrors on their quest to find the exit. One popular maze-