描述:
定义一个二维数组:
int maze[5][5] = { 0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, }; 它表示一个迷宫,其中的1表示墙壁,0表示可以走的路,只能横着走或竖着走,不能斜着走,要求编程序找出从左上角到右下角的最短路线。
一个5 × 5的二维数组,表示一个迷宫。数据保证有唯一解。
左上角到右下角的最短路径,格式如样例所示。
input:
0 1 0 0 0
0 1 0 1 0
0 0 0 0 0
0 1 1 1 0
0 0 0 1 0
output:
(0, 0)
(1, 0)
(2, 0)
(2, 1)
(2, 2)
(2, 3)
(2, 4)
(3, 4)
(4, 4)
该题的主要讲解和思路都写在注释中,方法简单,更方便食用哦
代码实现:
/*
广度优先搜索 BFS
执行顺序是,先用que保存所有的情况,一个一个进行向外衍生,
顺序,先执行第一个,判断第一个有多少种走法,全部储存到que中,然后分a,b;a用于遍历,b用于储存
用a向后推,遍历该是否满足,不满足的话进行该位置的下一个方向的判断,如果找到位置的话,就用b进行储存
que中的p的作用是保存下一步的方向,如果p[i] = 1,那么就对照dx进行坐标的加减。
注意:走过的地方都要进行标记,防止重复走。
*/
#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
int arr[10][10]; // 储存内容
bool used[10][10]; // 标记是否走过。
int fx = 0,fy = 0,endx = 4,endy = 4;
int dx[4] = {1,-1,0,0};// 坐标的移动,配合47,40...行的使用
int dy[4] = {0,0,1,-1};
struct point // 建立结构体用来记录走的方法
{
int x,y; // 记录坐标
int p[100]; // 记录下一步的方向
int steps; // 记录步数
}que[30],u; // que用来储存所以的情况,广泛遍历,
void bfs()
{
int a=0,b=0;
que[b].x = 0,que[b].y = 0,que[b].steps = 0,que[b].p[que[b].steps] = 0; // 储存初始位置的坐标,步数,方向
b++; // 向后推一位
used[fx][fy] = true; //标记已经走过了
while(1)
{
u = que[a++]; // 遍历,判断是否满足和记录在这个坐标上的下一个位置
if(u.x == endx&&u.y == endy) // 如果满足条件,输出
{
int xx = 0,yy = 0;
cout << "(" << xx << ", " << yy << ")" << endl;
for(int i = 1; i <= u.steps; i++)
{
xx = xx+dx[u.p[i]],yy = yy + dy[u.p[i]];
printf("(%d, %d)\n",xx,yy);
}
return ;
}
for(int i = 0; i <= 3; i++)
{
int nx = u.x+dx[i],ny = u.y+dy[i];
if(nx>=0&&nx<5&&ny>=0&&ny<5&&!used[nx][ny]&&arr[nx][ny] == 0) // 防止越界和去除不让走的和去除重复的
{
que[b].x = nx,que[b].y = ny; // 储存下一个位置(52-58);
que[b].steps = u.steps+1;
for(int i = 0; i <= u.steps; i++)
{
que[b].p[i] = u.p[i];
}
que[b].p[que[b].steps] = i;
b++;
used[nx][ny] = true; // 标记已经走过。
}
}
}
}
int main (void)
{
for(int i = 0;i < 5; i++) // 输入和初始化,不做解释。
{
for(int j = 0; j < 5;j++)
{
scanf("%d",&arr[i][j]);
}
}
memset(used,false,sizeof(used));
bfs();
return 0;
}