通俗理解BFS和DFS,附基本模板

1.BFS(宽度优先搜索):使用队列来保存未被检测的节点,按照宽度优先的顺序被访问和进出队列

打个比方:(1)类似于树的按层次遍历

     (2)你的眼镜掉在了地上,你趴在地上,你总是先摸离你最近的地方,如果没有,再摸远一点的地方……

 1 BFS算法:
 2 
 3 通常用队列(先进先出,FIFO)实现
 4 
 5 初始化队列Q;
 6 Q = {起点s};
 7 标记s为已访问;
 8 while(Q非空)
 9 {
10     取Q队首元素u;
11     u出队;
12     if(u==目标状态)
13     {
14         ……
15     }
16     else
17     {
18         所有与u相邻且未被访问的点进入队列;
19         标记u为已访问;
20     }
21 }

 

 1 //BFS算法框架
 2 #include<iostream>
 3 #include<cstdio>
 4 #include<cstring>
 5 #include<queue>
 6 #include<algorithm>
 7 using namespace std;
 8 
 9 const int maxn = 100;
10 bool mark[maxn][maxn]; //访问标记
11 int go[4][2] = {0,-1,1,0,0,1,-1,0}; //方向向量
12 
13 struct State
14 {
15     int x,y; //坐标位置
16     int step; //搜索步数记录
17 };
18 
19 State maze[maxn];
20 
21 bool CheckState(State s)
22 {
23     if(!mark[s.x][s.y]&&(边界条件满足)) //符合条件
24         return 1;
25     else //不符合条件
26         return 0;
27 }
28 
29 void BFS(State st)
30 {
31     queue<State> q;
32     State now,next;
33     st.step = 0; //步数清零;
34     q.push(st); //入队;
35     mark[st.x][st.y] = 1; //访问标记
36     while(!q.empty())
37     {
38         now = q.front(); //取队首元素进行拓展
39         q.pop(); //队首元素出队;
40         if(now == 目标状态) //出现目标状态,此时的step为最小值,做做相关处理后退出即可;
41         {
42             ……;
43             return ;
44         }
45         //如果没有到目标状态:
46         else
47         {
48             for(int i=0;i<4;i++)
49             {
50                 next.x = now.x + go[i][0];//按照规则生成下一个状态
51                 next.y = now.y + go[i][1];
52                 if(CheckState(next)) //如果状态满足条件则入队;
53                 {
54                     next.step = now.step + 1;
55                     q.push(next);
56                 }
57             }
58         }
59         return ;
60     }
61 }
62 
63 int main()
64 {
65     ……;
66     BFS();
67     ……;
68     return 0;
69 }

 

DFS (深度优先搜索):一直往下搜,知道找到解或者走不下去为止

打个比方:(1)类似于树的先根遍历

     (2)类似于你在走迷宫,你不能分身来站在每个走过的位置,所以,你只能不撞南墙不回头。

 

 1 DFS:
 2 
 3 使用栈来保存未被检测的节点,
 4 节点按照深度优先的次序被访问并依次压入栈中,并已相反的次序出栈进行新的检测。
 5 
 6 DFS(dep,……)//dep代表目前DFS的深度
 7 {
 8     if(找到解||走不下去了)
 9     {
10         ……;
11         return12     }
13     else
14     {
15         枚举下一种情况;
16         DFS(dep+1,……);
17     }
18 }

 

 1 //DFS算法框架:
 2 
 3 #include<iostream>
 4 #include<cstring>
 5 #include<cstdlib>
 6 using namespace std;
 7 
 8 const int maxn = 100;
 9 bool mark[maxn][maxn]; //访问标记
10 int maze[maxn][maxn]; //坐标范围
11 int go[4][2] = {0,-1,1,0,0,1,-1,0}; //方向向量
12 
13 bool CheckState(int x,int y)
14 {
15     if(!mark[x][y]&&……) //满足条件
16         return 1;
17     else //与约束条件冲突
18         return 0;
19 }
20 
21 void DFS(int x,int y)
22 {
23     mark[x][y] = 1; //标记该节点被访问过
24     if(maze[x][y] == G) //出现目标状态G
25     {
26         …… //做相应处理
27         return ;
28     }
29     else
30     {
31         for(int i=0;i<4;i++)
32             if(CheckState(x+go[i][0],y+go[i][1])) //按照规则生成下一个节点
33                 DFS(x+go[i][0],y+go[i][1]);
34     }
35     return ; //如果没有下层搜索点,则回溯;
36 }
37 
38 int main()
39 {
40     ……;
41     return 0;
42 }

 

posted @ 2018-12-11 09:22  HiCYP  阅读(2700)  评论(0编辑  收藏  举报