算法:队列与广度优先搜索(迷宫问题)
来源:互联网 发布:淘宝店铺异常,状态码-2 编辑:程序博客网 时间:2024/05/16 19:33
队列也是一组元素的集合,也提供两种基本操作:Enqueue(入队)将元素添加到队尾,Dequeue(出队)从队头取出元素并返回。就像排队买票一样,先来先服务,先入队的人也是先出队的,这种方式称为FIFO(First In First Out,先进先出),有时候队列本身也被称为FIFO。
下面我们用队列解决迷宫问题。程序如下:(参考《linux c 编程一站式学习》)
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
> File Name: breadth_search.c
> Author: Simba
> Mail: dameng34@163.com
> Created Time: 2012年12月24日 星期一 19时24分37秒
************************************************************************/
#include<stdio.h>
#define MAX_ROW 5
#define MAX_COL 5
struct point
{
int row, col, predecessor;
} queue[512];
int head = 0, tail = 0;
void enqueue(struct point p)
{
queue[tail++] = p;
}
struct point dequeue(void)
{
return queue[head++];
}
int is_empty(void)
{
return head == tail;
}
int maze[MAX_ROW][MAX_COL] =
{
{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},
};
void print_maze(void)
{
int i, j;
for (i = 0; i < MAX_ROW; i++)
{
for (j = 0; j < MAX_COL; j++)
printf("%d ", maze[i][j]);
putchar('\n');
}
printf("*********\n");
}
void visit(int row, int col)
{
struct point visit_point = { row, col, head - 1 };
maze[row][col] = 2;
enqueue(visit_point);
}
int main(void)
{
struct point p = { 0, 0, -1 };
maze[p.row][p.col] = 2;
enqueue(p);
while (!is_empty())
{
p = dequeue();
if (p.row == MAX_ROW - 1 /* goal */
&& p.col == MAX_COL - 1)
break;
if (p.col + 1 < MAX_COL /* right */
&& maze[p.row][p.col + 1] == 0)
visit(p.row, p.col + 1);
if (p.row + 1 < MAX_ROW /* down */
&& maze[p.row + 1][p.col] == 0)
visit(p.row + 1, p.col);
if (p.col - 1 >= 0 /* left */
&& maze[p.row][p.col - 1] == 0)
visit(p.row, p.col - 1);
if (p.row - 1 >= 0 /* up */
&& maze[p.row - 1][p.col] == 0)
visit(p.row - 1, p.col);
print_maze();
}
if (p.row == MAX_ROW - 1 && p.col == MAX_COL - 1)
{
printf("(%d, %d)\n", p.row, p.col);
while (p.predecessor != -1)
{
p = queue[p.predecessor];
printf("(%d, %d)\n", p.row, p.col);
}
}
else
printf("No path!\n");
return 0;
}
其实仍然可以像《用深度优先搜索解迷宫问题》一样用predecessor数组表示每个点的前趋,但我们可以换一种更方便的数据结构,直接在每个点的结构体中加一个成员表示前趋:
struct point { int row, col, predecessor; } queue[512];
int head = 0, tail = 0;
变量head和tail是队头和队尾指针,head总是指向队头,tail总是指向队尾的下一个元素。每个点的predecessor成员也是一个指针,指向它的前趋在queue数组中的位置。如下图所示:
这是一个静态分配的数组,每个数组元素都有row、col和predecessor三个成员,predecessor成员保存一个数组下标,指向数组中的另一个元素,这其实也是链表的一种形式,称为《静态链表》。
为了帮助理解,把这个算法改写成伪代码如下图:
从打印的搜索过程可以看出,这个算法的特点是沿各个方向同时展开搜索,每个可以走通的方向轮流往前走一步,这称为广度优先搜索(BFS,Breadth First Search)。探索迷宫和队列变化的过程如下图所示。
广度优先是一种步步为营的策略,每次都从各个方向探索一步,将前线推进一步,图中的虚线就表示这个前线,队列中的元素总是由前线的点组成的,可见正是队列先进先出的性质使这个算法具有了广度优先的特点。广度优先搜索还有一个特点是可以找到从起点到终点的最短路径,而深度优先搜索找到的不一定是最短路径。
- 算法:队列与广度优先搜索(迷宫问题)
- 广度优先搜索BFS(迷宫问题)
- 迷宫问题(广度优先搜索)
- 迷宫问题-广度优先搜索
- 迷宫问题-广度优先搜索
- 广度优先搜索:迷宫问题
- 【面试题】迷宫问题---广度优先搜索-----队列
- C语言广度优先搜索之迷宫(队列)
- 队列:广度优先搜索求解迷宫
- C++广度优先搜索算法之迷宫问题
- 利用深度优先搜索算法和广度优先搜索算法解迷宫问题
- Java算法---华为oj迷宫问题求解(广度优先搜索)
- 广度优先搜索-迷宫问题(算法基础 第8周)
- 数据结构---迷宫问题(不相交集、广度优先搜索)
- 迷宫问题(广度优先搜索,输出最短路径)
- 通过邻接表实现广度优先搜索(迷宫问题)
- 广度优先搜索--迷宫问题(poj 3984)
- Matlab 广度优先搜索求解迷宫问题
- hdu 3068
- FreeMarker初级攻略
- JSF参数传递方式
- OOM(out_of_memory) killer分析
- 设计模式之五S:动态代理模式(Dynamic Proxy Pattern)
- 算法:队列与广度优先搜索(迷宫问题)
- 输入中文,然后在输出,显示为乱码解决方法
- Android的设计与实现:卷I
- asp.net 错误编号的意义(400,500)
- is not in the sudoers file. This incident will be reported
- linux上 管理arp的一些工具
- 创建和使用Android Library工程
- java.lang.ClassCastException: cn.vlabs.csp.model.expotion.ExpoFeeConfig cannot be cast to java.lang.
- Java开发规范使用手册