算法与数据结构:二叉树的遍历
二叉树
简介
二叉树指树中节点的度不大于2的有序树
二叉树相关属性解释:
- 结点:包含一个数据元素及若干指向子树分支的信息。
- 结点的度:一个结点拥有子树的数目称为结点的度。
- 叶子结点:也称为终端结点,没有子树的结点或者度为零的结点。
- 分支结点:也称为非终端结点,度不为零的结点称为非终端结点。
- 树的度:树中所有结点的度的最大值。
- 结点的层次:从根结点开始,假设根结点为第1层,根结点的子节点为第2层,依此类推,如果某一个结点位于第L层,则其子节点位于第L+1层。
- 树的深度:也称为树的高度,树中所有结点的层次最大值
- 有序树:树中各棵子树的次序是有先后次序
- 无序树:树中各棵子树的次序没有先后次序
二叉树的遍历
深度优先DFS:前序(根左右)、中序(左根右)、后序(左右根)
广度优先BFS:层序遍历
前序遍历
-
递归方式
class Solution { // 递归法 private List<Integer> list = new ArrayList<>(); public List<Integer> preorderTraversal(TreeNode root) { if(root==null) return list; dfs(root); return list; } public void dfs(TreeNode root) { if(root==null) return; list.add(root.val); //*** dfs(root.left); dfs(root.right); } } -
迭代方式(使用栈)
class Solution { // 迭代法 不为空就push同时加入list,左右为空则pop不加入list public List<Integer> preorderTraversal(TreeNode root) { List<Integer> list = new ArrayList<>(); Stack<TreeNode> st = new Stack(); while(st.size() != 0 || root != null){ if(root != null){ st.push(root); list.add(root.val); //入栈取值 root = root.left; }else{ TreeNode tmp = st.pop(); root = tmp.right; } } return list; } }
中序遍历
-
递归方式
class Solution { // 递归方法比较简单 时间n,空间h(树的高度) private List<Integer> list = new ArrayList<>(); if(root==null) return list; dfs(root); return list; } public void dfs(TreeNode root) { if(root==null) return; dfs(root.left); list.add(root.val); //*** dfs(root.right); } } -
迭代方式(使用栈)
class Solution { // 迭代方法,用栈来实现 public List<Integer> inorderTraversal(TreeNode root) { List<Integer> list = new ArrayList<>(); // 栈中存的是TreeNode Stack<TreeNode> st = new Stack<>(); while(st.size()>0 || root != null){ if(root != null){ st.push(root); root = root.left; }else{ TreeNode tmp = st.pop(); list.add(tmp.val); //出栈取值 root = tmp.right; } } return list; } }
后序遍历
-
递归方式
class Solution { // 递归法 List<Integer> list = new ArrayList<>(); public List<Integer> postorderTraversal(TreeNode root) { if(root==null) return list; dfs(root); return list; } public void dfs(TreeNode root){ if(root==null) return; dfs(root.left); dfs(root.right); list.add(root.val); //*** } } -
迭代方式(使用栈)
class Solution { // 迭代法 比较特殊,中右左取值,然后逆序,仿照前序中左右写 public List<Integer> postorderTraversal(TreeNode root) { Stack<TreeNode> st = new Stack<>(); List<Integer> list = new ArrayList<>(); while(st.size() != 0 || root != null){ if(root != null){ list.add(root.val); st.push(root); root = root.right; }else{ TreeNode tmp = st.pop(); root = tmp.left; } } Collections.reverse(list); //使用Collections集合工具类 逆序 return list; } }
层序遍历
-
迭代法(使用队列)
class Solution { // 广度优先 迭代法 用队列Queue (深度优先的迭代法用栈Stack) public List<List<Integer>> levelOrder(TreeNode root) { Queue<TreeNode> q = new LinkedList<>(); List<List<Integer>> list = new ArrayList<>(); if(root==null) return list; q.add(root); while(!q.isEmpty()){ // 记录队列长度 int size = q.size(); List<Integer> tmp = new ArrayList<>(); // 根据队列长度取元素,取出一个元素后,放入其左右节点 for(int i=0; i<size; i++){ TreeNode cur = q.poll(); tmp.add(cur.val); if(cur.left != null) q.offer(cur.left); if(cur.right != null) q.offer(cur.right); } list.add(tmp); } return list; } }
浙公网安备 33010602011771号