用栈和队列实现BFS和DFS算法
1.BFS(宽度优先遍历)
1、从顶点v出发遍历图G的算法描述如下:
①访问V0
②假设最近一层的访问顶点依次为v1v2v3vk则依次访问v1,v2,v3…vk的未被访问的邻接点
③重复②知道没有未被访问的邻接点为止
2、心得:bfs算法其实就是一种层次遍历算法。从算法描述可以看到该算法要用到队列这一数据结构。
Set集合的作用是用来判断当前节点是不是已经访问过,加到队列中去了,避免重复添加。
3、算法代码:
import java.util.HashSet;
import java.util.LinkedList;
import java.util.Queue;
public class Code_01_BFS {
public static void bfs(Node node) {
if (node == null) {
return;
}
Queue<Node> queue = new LinkedList<>();
HashSet<Node> map = new HashSet<>();//表示该节点在不在队列里
queue.add(node);
map.add(node);
while (!queue.isEmpty()) {
Node cur = queue.poll();
System.out.println(cur.value);
for (Node next : cur.nexts) {
if (!map.contains(next)) {//map中不包含这个节点就加入队列和set集合
map.add(next);
queue.add(next);
}
}
}
}
}
2. DFS算法(深度优先遍历)
1、从顶点v出发深度遍历图G的算法
① 访问v
② 依次从顶点v未被访问的邻接点出发深度遍历。
2、心得:dfs算法通常的做法是使用其递归特性,使得算法代码简洁。但也由于递归使得算法难以理解,所以这里使用栈来实现,通俗易懂。
_ 对应的语句都有解释,Set集合在这里也是用来表示该节点是不是被加入都栈中,避免重复添加_
3、算法代码:
public class Code_02_DFS {
//非递归实现
public static void dfs(Node node) {
if (node == null) {
return;
}
Stack<Node> stack = new Stack<>();
HashSet<Node> set = new HashSet<>();//表示该节点是不是进过栈里
stack.add(node);
set.add(node);
System.out.println(node.value);
while (!stack.isEmpty()) {
Node cur = stack.pop();//栈中不断弹出进行判断是不是还存在邻居
for (Node next : cur.nexts) {
//找到一个邻居就执行
if (!set.contains(next)) {//邻居节点如果没有进过set就执行进栈
stack.push(cur);//把当前节点和邻接节点都放入栈
stack.push(next);
set.add(next);
System.out.println(next.value);//打印邻接节点
break;
}
}
}