java之树的遍历

本文介绍了树的两种基本遍历方式:深度优先遍历(DFS)和广度优先遍历(BFS)。深度优先遍历优先探索尽可能深的子树,而广度优先遍历则逐层遍历树的所有节点。通过具体的Java实现代码示例,读者可以更好地理解这两种遍历方法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

树的深度优先遍历和广度优先遍历

深度优先遍历(Depth First Search,DFS)和广度优先遍历(Breadth First Search,BFS)是两种遍历树中元素的方式。

深度优先遍历(DFS):


对于上述tree来说,DFS的遍历结果为:A B D E C F G

如果某个节点有子节点和兄弟节点,那么优先遍历子节点,左子树优先于右子树,直到子树都被深度遍历后,然后再遍历兄弟节点及其子树。

由于不会立马遍历兄弟子树,使用栈来记录未被遍历的节点,这里说一下为何要使用栈结构,栈具有先进后出的特点,所以将不需要立马遍历的结点压入栈后,也不会优先处理。

java实现

package tree;

import java.util.LinkedList;
import java.util.List;
import java.util.Stack;

public class DFS {
	//深度优先遍历方法
	public static void depthFirstSearch(Node root) {
		Stack<Node> stack = new Stack<Node>();//在遍历过程中存储树的结点信息,FILO的特点记录了处理的顺序
		List<Node> list = new LinkedList<Node>();//存放遍历结果
		Node tempnode  = root;
		stack.push(tempnode);//根结点入栈
		
		while(!stack.isEmpty()) {//当栈为空,表示整棵树已经全部被遍历
			tempnode = stack.pop();
			list.add(tempnode);
			if(tempnode.rightnode != null) {
				stack.push(tempnode.rightnode);//将分支结点压入栈,为了保证先处理左子树,再处理右子树,必须先将右子树压入栈
			}
			
			if(tempnode.leftnode != null) {
				stack.push(tempnode.leftnode);
			}
			
		}
		
		for(Node tn :list) {
			System.out.print(tn.val+",");
		}
	}
	
	public static void main(String[] args) {
		Node n1 = new Node(1);
		Node n2= new Node(2);
		Node n3 = new Node(3);
		Node n4 = new Node(4);
		Node n5 = new Node(5);
		Node n6 = new Node(6);
		Node n7 = new Node(7);
		
		n1.leftnode = n2;
		n1.rightnode = n3;
		
		n2.leftnode = n4;
		n2.rightnode = n5;
		
		n3.leftnode = n6;
		n3.rightnode = n7;
		
		DFS.depthFirstSearch(n1);
	}
}
class Node{
	int val;
	Node leftnode;
	Node rightnode;
	Node(int val){
		this.val = val;
	}
}

广度优先遍历(BFS

广度优先遍历和深度优先遍历是相反的,即如果某个节点有子节点和兄弟节点,那么优先遍历兄弟节点。使用队列的数据来存储树中的结点。

package tree;

import java.util.LinkedList;
import java.util.List;
import java.util.Queue;

public class BFS {
	public static void breadthFirstSearch(Node root) {
		Node tempnode = root;
		Queue<Node> queue = new LinkedList<Node>();
		List<Node> list = new LinkedList<Node>();
		queue.add(tempnode);
		
		while(!queue.isEmpty()) {
			tempnode = queue.remove();
			list.add(tempnode);
			if(tempnode.leftnode!= null) {
				queue.add(tempnode.leftnode);
			}
			if(tempnode.rightnode != null) {
				queue.add(tempnode.rightnode);
			}
		}
		
		for(Node tn :list) {
			System.out.print(tn.val+",");
		}
	}
	public static void main(String[] args) {
		Node n1 = new Node(1);
		Node n2= new Node(2);
		Node n3 = new Node(3);
		Node n4 = new Node(4);
		Node n5 = new Node(5);
		Node n6 = new Node(6);
		Node n7 = new Node(7);
		
		n1.leftnode = n2;
		n1.rightnode = n3;
		
		n2.leftnode = n4;
		n2.rightnode = n5;
		
		n3.leftnode = n6;
		n3.rightnode = n7;
		
		DFS.depthFirstSearch(n1);
	}
}
class Node{
	int val;
	Node leftnode;
	Node rightnode;
	Node(int val){
		this.val = val;
	}
}



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值