文章目录

  • 树的遍历
    • 先序遍历(单栈)
      • 例题:
    • 中序遍历(单栈)
      • 例题:
    • 后续遍历(双栈)
      • 例题:
    • 层次遍历(队列)
      • 例题:
    • 二叉树的最大深度
      • 例题:
  • 判断树的类型
    • 是否搜索二叉树
      • 例题:
    • 是否完全二叉树
      • 例图:
    • 是否满二叉树
    • 是否平衡二叉树
      • 例题:[110. 平衡二叉树 - 力扣(LeetCode) (leetcode-cn.com)](https://leetcode-cn.com/problems/balanced-binary-tree/)
  • 节点的公共祖先
    • 例题:

推荐视频:

一周刷爆LeetCode,算法大神左神(左程云)耗时100天打造算法与数据结构基础到高级全家桶教程,直击BTAJ等一线大厂必问算法面试题真题详解_哔哩哔哩_bilibili

树的遍历

递归序:看视频吧

  • 先序遍历 – 头左右
  • 先序遍历的变体 – 头右左 (跟后续遍历 相反 即 使用双栈可以实现后序遍历
  • 中序遍历 – 左头右
  • 后续遍历 – 左右头

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-7nXaCHly-1646635857542)(C:\Users\dancerHoan\AppData\Roaming\Typora\typora-user-images\image-20220301100725128.png)]

class Solution {public void preOrder(TreeNode root){if(root==null){return;}//先序遍历 在这里处理节点 System.out.println(root.val)preOrder(root.left,l);//中序遍历 在这里处理节点 System.out.println(root.val)preOrder(root.right,l);//后序遍历 在这里处理节点 System.out.println(root.val)}
}

先序遍历(单栈)

实现步骤:
Stack<Node> s = new Stack<>();1.从栈中弹出一个节点 Node n = s.pop();
2.打印(处理) 该节点
3.将孩子节点 从右至左 依次压栈
List<Node> children = n.children;
for(int i=children.size()-1;i>=0;i--){Node node = children.get(i);s.push(node);
}
4.循环 while(!s.isEmpty())

例题:

589. N 叉树的前序遍历 - 力扣(LeetCode) (leetcode-cn.com)

class Solution {public List<Integer> preorder(Node root) {Stack<Node> s = new Stack<>();List<Integer> l = new ArrayList<>();if (root == null) {return l;}s.push(root);while (!s.isEmpty()) {Node n = s.pop();l.add(n.val);List<Node> children = n.children;for(int i=children.size()-1;i>=0;i--){Node node = children.get(i);s.push(node);}// 倒叙遍历,当然这个方法很蠢 可以先将链表反转如下// Collections.reverse(node.children);// for (Node item : node.children) {//   stack.add(item);// }}return l;}
}

144. 二叉树的前序遍历 - 力扣(LeetCode) (leetcode-cn.com)

class Solution {public List<Integer> preorderTraversal(TreeNode root) {List<Integer> l = new ArrayList<>();Stack<TreeNode> s = new Stack<>();if(root==null){return l;}s.push(root);while(!s.isEmpty()){TreeNode n = s.pop();l.add(n.val);if(n.right !=null){s.push(n.right);}if(n.left != null){s.push(n.left);}}return l;}
}

中序遍历(单栈)

中序遍历 – 左头右

整棵树左边界进栈,依次弹出的过程中打印,对弹出节点的右树重复。

打印顺序是 左头右

  1. 将左节点循环入栈 s.push(root); root = root.left;
  2. 若左节点不存在 则说明 上一次压栈的节点为 头节点
  3. 将头节点 出栈后 指针指向其右节点 root = root.right;

Tips: