94. 二叉树的中序遍历

给定一个二叉树,返回它的中序 遍历。

示例:

输入: [1,null,2,3]

1



2

/

3

输出: [1,3,2]

进阶: 递归算法很简单,你可以通过迭代算法完成吗?

//中序遍历 必会
//两个思路 递归、栈 //第三种方法 颜色标记法 来及网友Henry
//核心思想,搞一个栈用来存储遍历过的,根据要求遍历的顺序,将可以放入的指为灰色,不能的为白色
//不断弹出栈顶元素进行判断
//本质为自己手动维护一个递归的栈 //第四种方法 莫里斯中序遍历 通过改变树的结构的遍历(不做要求)

solution1 递归

class Solution {
public List<Integer> inorderTraversal(TreeNode root) {
List <Integer> res = new ArrayList <> ();
helper(root, res);
return res;
}
private void helper(TreeNode root, List <Integer> res) {
if (root != null) {
if (root.left != null) {
helper(root.left, res);
}
res.add(root.val);
if (root.right != null) {
helper(root.right, res);
}
}
}
}

solution2 栈

class Solution {
public List<Integer> inorderTraversal(TreeNode root) {
List <Integer> res = new ArrayList <> ();
Stack <TreeNode> stack = new Stack<>();
TreeNode curr = root;
while (curr != null || !stack.isEmpty()){
//先把根结点放入stack
while (curr != null) {
stack.push(curr);
curr = curr.left;
}
curr = stack.pop();
res.add(curr.val);
curr = curr.right;
}
return res;
}
}

solution3 颜色标记法

class Solution {
class ColorNode{
TreeNode node;
String color;
public ColorNode(TreeNode node,String color){
this.node = node;
this.color = color;
}
}
public List<Integer> inorderTraversal(TreeNode root) {
if (root == null) return new ArrayList<Integer>(); List<Integer> res = new ArrayList<>();
Stack<ColorNode> st = new Stack<>();
st.push(new ColorNode(root,"white"));
while (!st.isEmpty()){
ColorNode cn = st.pop(); //先把结点pop出来
if (cn.color == "white"){
if (cn.node.right != null) st.push(new ColorNode(cn.node.right,"white"));
st.push(new ColorNode(cn.node,"grey"));
if (cn.node.left != null) st.push(new ColorNode(cn.node.left,"white"));
}else {
res.add(cn.node.val);
}
}
return res;
}
}

144. 二叉树的前序遍历

给定一个二叉树,返回它的 前序 遍历。

示例:

输入: [1,null,2,3]

1



2

/

3

输出: [1,2,3]

进阶: 递归算法很简单,你可以通过迭代算法完成吗?

solution1 递归

class Solution {
public List<Integer> preorderTraversal(TreeNode root) {
List<Integer> res = new ArrayList<>();
helper(root,res);
return res; }
private void helper(TreeNode root,List<Integer> res){
if (root == null) return;
res.add(root.val);
helper(root.left, res);
helper(root.right, res);
}
}

solution2 用栈进行迭代

//用栈保存根结点,最后一棵树放在最上方
class Solution {
public List<Integer> preorderTraversal(TreeNode root) {
List<Integer> res = new ArrayList<>();
Stack<TreeNode> st = new Stack<>();
TreeNode curr = root;
while (curr != null || !st.isEmpty()){ //防止一开始为空
while (curr != null) {
res.add(curr.val);
st.push(curr);
curr = curr.left;
}
curr = st.pop().right; }
return res; }
}

solution3 颜色标记法

class Solution {
class ColorNode{
TreeNode node;
String color;
public ColorNode(TreeNode node,String color){
this.node = node;
this.color = color;
}
}
public List<Integer> preorderTraversal(TreeNode root) {
if (root == null) return new ArrayList<>();
List<Integer> res = new ArrayList<>();
Stack<ColorNode> st = new Stack<>();
st.push(new ColorNode(root,"white"));
while (!st.isEmpty()){
ColorNode cn = st.pop();
if (cn.color == "white"){
if (cn.node.right != null) st.push(new ColorNode(cn.node.right,"white"));
if (cn.node.left != null) st.push(new ColorNode(cn.node.left,"white"));
st.push(new ColorNode(cn.node,"grey"));
}else {
res.add(cn.node.val);
}
}
return res; }
}

145. 二叉树的后序遍历

给定一个二叉树,返回它的 后序 遍历。

示例:

输入: [1,null,2,3]

1



2

/

3

输出: [3,2,1]

进阶: 递归算法很简单,你可以通过迭代算法完成吗?

 //三种思路
//新递归(终结条件+当前层+下探层+(清理本层))
//迭代 (把左树和根压入栈,再从栈弹出,判断是否有右子树)
//颜色标记

solution1 递归

class Solution {
public List<Integer> postorderTraversal(TreeNode root) {
List<Integer> res = new ArrayList<>();
helper(root,res);
return res;
}
private void helper(TreeNode root,List<Integer> list){
if(root==null) return;
helper(root.left,list);
helper(root.right,list);
list.add(root.val);
} }

solution2 栈+迭代

class Solution {
public List<Integer> postorderTraversal(TreeNode root) {
if (root == null) return new ArrayList<>();
List<Integer> res = new ArrayList<>();
Stack<TreeNode> st = new Stack<>();
TreeNode curr = root;
TreeNode last = null;//用于遍历右子树时,存储上一个节点
while(curr!=null || !st.isEmpty()){
//压根和左子树
while(curr!=null){
st.push(curr);
curr = curr.left;
}
curr = st.peek(); //判断是否有右数
if(curr.right == null || curr.right == last){ //右边为空,或者已经遍历过了
res.add(st.pop().val);
last = curr;//记录
curr = null;
}else{
curr = curr.right;
}
}
return res;
}
}

solution3 颜色标记法

class Solution {
class ColorNode{
TreeNode node;
String color;
public ColorNode(TreeNode root,String color){
this.node = root;
this.color = color;
}
}
public List<Integer> postorderTraversal(TreeNode root) {
if (root == null) return new ArrayList<>();
List<Integer> res = new ArrayList<>();
Stack<ColorNode> st = new Stack<>();
st.push(new ColorNode(root,"white"));
while(!st.isEmpty()){
ColorNode cn = st.pop();
if(cn.color == "white"){
st.push(new ColorNode(cn.node,"grey"));
if (cn.node.right!= null) st.push(new ColorNode(cn.node.right,"white"));
if (cn.node.left!= null) st.push(new ColorNode(cn.node.left,"white"));
}else{
res.add(cn.node.val);
}
}
return res;
}
}

LeetCode 数、二叉树、二叉搜索树篇(94、144、145)的更多相关文章

  1. LeetCode:验证二叉搜索树【98】

    LeetCode:验证二叉搜索树[98] 题目描述 给定一个二叉树,判断其是否是一个有效的二叉搜索树. 假设一个二叉搜索树具有如下特征: 节点的左子树只包含小于当前节点的数. 节点的右子树只包含大于当 ...

  2. C#LeetCode刷题-二叉搜索树

    二叉搜索树篇 # 题名 刷题 通过率 难度 220 存在重复元素 III   19.3% 中等 315 计算右侧小于当前元素的个数   31.9% 困难 327 区间和的个数   29.5% 困难 3 ...

  3. Leetcode:235. 二叉搜索树的最近公共祖先

    Leetcode:235. 二叉搜索树的最近公共祖先 Leetcode:235. 二叉搜索树的最近公共祖先 Talk is cheap . Show me the code . /** * Defin ...

  4. Leetcode:530. 二叉搜索树的最小绝对差

    Leetcode:530. 二叉搜索树的最小绝对差 Leetcode:530. 二叉搜索树的最小绝对差 Talk is cheap . Show me the code . /** * Definit ...

  5. 代码随想录算法训练营day23 | leetcode 669. 修剪二叉搜索树 ● 108.将有序数组转换为二叉搜索树 ● 538.把二叉搜索树转换为累加树

    LeetCode 669. 修剪二叉搜索树 分析1.0 递归遍历树时删除符合条件(不在区间中)的节点-如何遍历如何删除 如果当前节点大于范围,递归左树,反之右树 当前节点不在范围内,删除它,把它的子树 ...

  6. 树(二叉树 & 二叉搜索树 & 哈夫曼树 & 字典树)

    树:n(n>=0)个节点的有限集.有且只有一个root,子树的个数没有限制但互不相交.结点拥有的子树个数就是该结点的度(Degree).度为0的是叶结点,除根结点和叶结点,其他的是内部结点.结点 ...

  7. LeetCode 98 验证二叉搜索树

    题目: 给定一个二叉树,判断其是否是一个有效的二叉搜索树. 假设一个二叉搜索树具有如下特征: 节点的左子树只包含小于当前节点的数. 节点的右子树只包含大于当前节点的数. 所有左子树和右子树自身必须也是 ...

  8. Leetcode 98 验证二叉搜索树 Python实现

    给定一个二叉树,判断其是否是一个有效的二叉搜索树. 假设一个二叉搜索树具有如下特征: 节点的左子树只包含小于当前节点的数. 节点的右子树只包含大于当前节点的数. 所有左子树和右子树自身必须也是二叉搜索 ...

  9. LeetCode 98. 验证二叉搜索树(Validate Binary Search Tree)

    题目描述 给定一个二叉树,判断其是否是一个有效的二叉搜索树. 假设一个二叉搜索树具有如下特征: 节点的左子树只包含小于当前节点的数. 节点的右子树只包含大于当前节点的数. 所有左子树和右子树自身必须也 ...

  10. 【LeetCode】不同二叉搜索树

    [问题] 卡特兰(Catalan)数来源于卡特兰解决凸n+2边形的剖分时得到的数列Cn,在数学竞赛.信息学竞赛.组合数学.计算机编程等方面都会有其不同侧面的介绍.卡特兰问题的解决过程应用了大量的映射方 ...

随机推荐

  1. 第六单元《管理学进展》单元测试 mooc

    第六单元<管理学进展>单元测试 返回 本次得分为:10.00/10.00, 本次测试的提交时间为:2020-08-30, 如果你认为本次测试成绩不理想,你可以选择 再做一次 . 1 判断( ...

  2. 入门篇-其之五-Java运算符(上)

    一元运算符之正负号 Java支持多种一元运算符,一元运算符中的"一元"是指一个操作数.我们初中学过的正负号就属于一元运算符,因为正负号后面只有一个数字. 正数使用+表示,其中+可以 ...

  3. 【Unity3D】Cesium加载大地图

    1 前言 ​ Cesium 是一个地球可视化平台和工具链,具有数据切片.数据分发.三维可视等功能. ​ Cesium 支持 JS.Unity.Unreal.O3DE.Omniverse 等平台,框架如 ...

  4. gson如何序列化子类

    需求 目前有一个需求,不同对象有一些公共属性,分别也有一些不同的属性.对方传过来的json字符串中,把这些对象组成了一个数组返回过来的.这样该如何反序列化呢? 举例 定义Person类.Student ...

  5. 【虹科干货】Redis 开发者需要了解的缓存驱逐策略

    在你搭建并配置了一个Redis数据库之后,Redis成功地提升了应用程序性能.然而这里有一个潜在问题,随着缓存数据的快速增加和内存占用率的逐渐上升,你很快会发现Redis缓存容量即将达到硬件存储容量上 ...

  6. Python合并多个Excel文件中的指定sheet

    本文将介绍一个用于合并多个Excel文件中指定sheet的Python代码.这个功能可以方便地整理和分析数据.我们将逐步解释代码的每个部分,并提供示例用法. 导入库 首先,我们导入了需要使用的三个库: ...

  7. STM32CUBEIDE中 Debug 和 Release 的作用/区别/使用场景

    基本主流IDE都有该功能选项例如Keil MDK, IAR, Eclipse, VS等, 这里使用STM32CUBEIDE来举例 创建STM32CUBEIDE工程后默认有2个目标选项 Debug / ...

  8. 你真的了解@Async吗?

    使用场景: 开发中会碰到一些耗时较长或者不需要立即得到执行结果的逻辑,比如消息推送.商品同步等都可以使用异步方法,这时我们可以用到@Async.但是直接使用 @Async 会有风险,当我们没有指定线程 ...

  9. Educational Codeforces Round 102 (Rated for Div. 2) A~D题

    写在前边 链接:Educational Codeforces Round 102 (Rated for Div. 2) 第一场打CF,过了AB两题,不过速度挺慢,C题属实没看懂,D题写了个常规做法之后 ...

  10. 升级到 Pulsar3.0 后深入了解 JWT 鉴权

    背景 最近在测试将 Pulsar 2.11.2 升级到 3.0.1的过程中碰到一个鉴权问题,正好借着这个问题充分了解下 Pulsar 的鉴权机制是如何运转的. Pulsar 支持 Namespace/ ...