树作为特殊的图,所以图的DFS和BFS在树中仍可以使用。以下以二叉树来讲述。
深度优先遍历(DFS)
深度优先遍历主要思路是从图中一个未访问的顶点 V 开始,沿着一条路一直走到底,然后从这条路尽头的节点回退到上一个节点,再从另一条路开始走到底,不断递归重复此过程,直到所有的顶点都遍历完成。
深度优先遍历(BFS)
(1)递归实现
public void dfs(Node node) {
if(node==null) {
return;
}
else {
System.out.println(node.data);
dfs(node.left);
dfs(node.right);
}
}
(2)非递归实现(利用栈实现)
使用栈来将要遍历的节点压栈,然后出栈后检查此节点是否还有未遍历的节点,有的话压栈,没有的话不断回溯(出栈)。
//DFS非递归实现
public void dfswithstack(Node root) {
if(root==null) {
return;
}
Stack<Node> stack = new Stack<>();//定义一个栈对象
stack.push(root);
while(!stack.isEmpty()) {//如果此步不理解,可画图理解
Node treenode=stack.pop();
System.out.println(treenode.data);
if(treenode.right!=null) {
stack.push(treenode.right);
}
if(treenode.left!=null) {
stack.push(treenode.left);
}
}
}
广度优先遍历(DFS)
//BFS的实现
public void bfs(Node root) {
if(root==null) {
return;
}
Queue<Node> stack=new LinkedList<>();//Queue为接口,必须有子类实现,定义一个队列对象
stack.add(root);
while(!stack.isEmpty()) {
Node treenode=stack.poll();
System.out.println(treenode.data);
if(treenode.left!=null) {
stack.add(treenode.left);
}
if(treenode.right!=null) {
stack.add(treenode.right);
}
}
}
传进来的都是根结点。
最后附一段测试代码。
package com.liubulong;
import java.util.LinkedList;
import java.util.Queue;
import java.util.Stack;
public class Demo11 {
public static void main(String[] args) {
// TODO 自动生成的方法存根
DfsBinaryTree bt=new DfsBinaryTree();
Node root01 = bt.root;
bt.dfswithstack(root01);
System.out.println("********");
bt.bfs(root01);
}
}
class DfsBinaryTree{
Node root;//根结点
public DfsBinaryTree() {
root=new Node("A");
createBinaryTree();
}
public void createBinaryTree() {
Node node1=new Node("B");
Node node2=new Node("C");
Node node3=new Node("D");
Node node4=new Node("E");
Node node5=new Node("F");
root.left=node1;
root.right=node2;
node1.left=node3;
node1.right=node4;
node2.right=node5;
}
//DFS递归实现
public void dfs(Node node) {
if(node==null) {
return;
}
else {
System.out.println(node.data);
dfs(node.left);
dfs(node.right);
}
}
//DFS非递归实现
public void dfswithstack(Node root) {
if(root==null) {
return;
}
Stack<Node> stack = new Stack<>();//Stack为类,定义一个栈对象
stack.push(root);
while(!stack.isEmpty()) {//如果此步不理解,可画图理解
Node treenode=stack.pop();
System.out.println(treenode.data);
if(treenode.right!=null) {
stack.push(treenode.right);
}
if(treenode.left!=null) {
stack.push(treenode.left);
}
}
}
//BFS的实现
public void bfs(Node root) {
if(root==null) {
return;
}
Queue<Node> stack=new LinkedList<>();//Queue为接口,必须有子类实现,定义一个队列对象
stack.add(root);
while(!stack.isEmpty()) {
Node treenode=stack.poll();
System.out.println(treenode.data);
if(treenode.left!=null) {
stack.add(treenode.left);
}
if(treenode.right!=null) {
stack.add(treenode.right);
}
}
}
}
class Node{
String data;
Node left;
Node right;
//构造器
public Node(String data) {
this.data=data;
}
}