<p align="center">
  <a href="https://mp.weixin.qq.com/s/RsdcQ9umo09R6cfnwXZlrQ"><img src="https://img.shields.io/badge/PDF下载-代码随想录-blueviolet" alt=""></a>
  <a href="https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw"><img src="https://img.shields.io/badge/刷题-微信群-green" alt=""></a>
  <a href="https://space.bilibili.com/525438321"><img src="https://img.shields.io/badge/B站-代码随想录-orange" alt=""></a>
  <a href="https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ"><img src="https://img.shields.io/badge/知识星球-代码随想录-blue" alt=""></a>
</p>
<p align="center"><strong>欢迎大家<a href="https://mp.weixin.qq.com/s/tqCxrMEU-ajQumL1i8im9A">参与本项目</a>，贡献其他语言版本的代码，拥抱开源，让更多学习算法的小伙伴们收益！</strong></p>

# 二叉树：总结篇！（需要掌握的二叉树技能都在这里了）

> 力扣二叉树大总结！

不知不觉二叉树已经和我们度过了**三十三天**，[「代码随想录」](https://img-blog.csdnimg.cn/20200815195519696.png)里已经发了**三十三篇二叉树的文章**，详细讲解了**30+二叉树经典题目**，一直坚持下来的录友们一定会二叉树有深刻理解了。

在每一道二叉树的题目中，我都使用了**递归三部曲**来分析题目，相信大家以后看到二叉树，看到递归，都会想：返回值、参数是什么？终止条件是什么？单层逻辑是什么？

而且**几乎每一道题目我都给出对应的迭代法**，可以用来进一步提高自己。

下面Carl把分析过的题目分门别类，可以帮助新录友循序渐进学习二叉树，也方便老录友面试前快速复习，看到一个标题，就回想一下对应的解题思路，这样很快就可以系统性的复习一遍二叉树了。

公众号的发文顺序，就是循序渐进的，所以如下分类基本就是按照文章发文顺序来的，我再做一个系统性的分类。

## 二叉树的理论基础

* [关于二叉树，你该了解这些！](https://mp.weixin.qq.com/s/_ymfWYvTNd2GvWvC5HOE4A)：二叉树的种类、存储方式、遍历方式、定义方式

## 二叉树的遍历方式

*  深度优先遍历
    * [二叉树：前中后序递归法](https://mp.weixin.qq.com/s/PwVIfxDlT3kRgMASWAMGhA)：递归三部曲初次亮相
    * [二叉树：前中后序迭代法（一）](https://mp.weixin.qq.com/s/c_zCrGHIVlBjUH_hJtghCg)：通过栈模拟递归
    * [二叉树：前中后序迭代法（二）统一风格](https://mp.weixin.qq.com/s/WKg0Ty1_3SZkztpHubZPRg)
* 广度优先遍历
    * [二叉树的层序遍历](https://mp.weixin.qq.com/s/Gb3BjakIKGNpup2jYtTzog)：通过队列模拟


## 求二叉树的属性

* [二叉树：是否对称](https://mp.weixin.qq.com/s/Kgf0gjvlDlNDfKIH2b1Oxg)
    * 递归：后序，比较的是根节点的左子树与右子树是不是相互翻转
    * 迭代：使用队列/栈将两个节点顺序放入容器中进行比较
* [二叉树：求最大深度](https://mp.weixin.qq.com/s/guKwV-gSNbA1CcbvkMtHBg)
    * 递归：后序，求根节点最大高度就是最大深度，通过递归函数的返回值做计算树的高度
    * 迭代：层序遍历
* [二叉树：求最小深度](https://mp.weixin.qq.com/s/BH8-gPC3_QlqICDg7rGSGA)
    * 递归：后序，求根节点最小高度就是最小深度，注意最小深度的定义
    * 迭代：层序遍历
* [二叉树：求有多少个节点](https://mp.weixin.qq.com/s/2_eAjzw-D0va9y4RJgSmXw)
    * 递归：后序，通过递归函数的返回值计算节点数量
    * 迭代：层序遍历
* [二叉树：是否平衡](https://mp.weixin.qq.com/s/isUS-0HDYknmC0Rr4R8mww)
    * 递归：后序，注意后序求高度和前序求深度，递归过程判断高度差
    * 迭代：效率很低，不推荐
* [二叉树：找所有路径](https://mp.weixin.qq.com/s/Osw4LQD2xVUnCJ-9jrYxJA)
    * 递归：前序，方便让父节点指向子节点，涉及回溯处理根节点到叶子的所有路径
    * 迭代：一个栈模拟递归，一个栈来存放对应的遍历路径
* [二叉树：递归中如何隐藏着回溯](https://mp.weixin.qq.com/s/ivLkHzWdhjQQD1rQWe6zWA)
    * 详解[二叉树：找所有路径](https://mp.weixin.qq.com/s/Osw4LQD2xVUnCJ-9jrYxJA)中递归如何隐藏着回溯
* [二叉树：求左叶子之和](https://mp.weixin.qq.com/s/gBAgmmFielojU5Wx3wqFTA)
    * 递归：后序，必须三层约束条件，才能判断是否是左叶子。
    * 迭代：直接模拟后序遍历
* [二叉树：求左下角的值](https://mp.weixin.qq.com/s/MH2gbLvzQ91jHPKqiub0Nw)
    * 递归：顺序无所谓，优先左孩子搜索，同时找深度最大的叶子节点。
    * 迭代：层序遍历找最后一行最左边
* [二叉树：求路径总和](https://mp.weixin.qq.com/s/6TWAVjxQ34kVqROWgcRFOg)
    * 递归：顺序无所谓，递归函数返回值为bool类型是为了搜索一条边，没有返回值是搜索整棵树。
    * 迭代：栈里元素不仅要记录节点指针，还要记录从头结点到该节点的路径数值总和


## 二叉树的修改与构造

* [翻转二叉树](https://mp.weixin.qq.com/s/6gY1MiXrnm-khAAJiIb5Bg)
    * 递归：前序，交换左右孩子
    * 迭代：直接模拟前序遍历
* [构造二叉树](https://mp.weixin.qq.com/s/7r66ap2s-shvVvlZxo59xg)
    * 递归：前序，重点在于找分割点，分左右区间构造
    * 迭代：比较复杂，意义不大
* [构造最大的二叉树](https://mp.weixin.qq.com/s/1iWJV6Aov23A7xCF4nV88w)
    * 递归：前序，分割点为数组最大值，分左右区间构造
    * 迭代：比较复杂，意义不大
* [合并两个二叉树](https://mp.weixin.qq.com/s/3f5fbjOFaOX_4MXzZ97LsQ)
    * 递归：前序，同时操作两个树的节点，注意合并的规则
    * 迭代：使用队列，类似层序遍历

## 求二叉搜索树的属性

* [二叉搜索树中的搜索](https://mp.weixin.qq.com/s/vsKrWRlETxCVsiRr8v_hHg)
    * 递归：二叉搜索树的递归是有方向的
    * 迭代：因为有方向，所以迭代法很简单
* [是不是二叉搜索树](https://mp.weixin.qq.com/s/8odY9iUX5eSi0eRFSXFD4Q)
    * 递归：中序，相当于变成了判断一个序列是不是递增的
    * 迭代：模拟中序，逻辑相同
* [求二叉搜索树的最小绝对差](https://mp.weixin.qq.com/s/Hwzml6698uP3qQCC1ctUQQ)
    * 递归：中序，双指针操作
    * 迭代：模拟中序，逻辑相同
* [求二叉搜索树的众数](https://mp.weixin.qq.com/s/KSAr6OVQIMC-uZ8MEAnGHg)
    * 递归：中序，清空结果集的技巧，遍历一遍便可求众数集合
    * 迭代：模拟中序，逻辑相同
* [二叉搜索树转成累加树](https://mp.weixin.qq.com/s/hZtJh4T5lIGBarY-lZJf6Q)
    * 递归：中序，双指针操作累加
    * 迭代：模拟中序，逻辑相同

## 二叉树公共祖先问题

* [二叉树的公共祖先问题](https://mp.weixin.qq.com/s/n6Rk3nc_X3TSkhXHrVmBTQ)
    * 递归：后序，回溯，找到左子树出现目标值，右子树节点目标值的节点。
    * 迭代：不适合模拟回溯
* [二叉搜索树的公共祖先问题](https://mp.weixin.qq.com/s/Ja9dVw2QhBcg_vV-1fkiCg)
    * 递归：顺序无所谓，如果节点的数值在目标区间就是最近公共祖先
    * 迭代：按序遍历

## 二叉搜索树的修改与构造

* [二叉搜索树中的插入操作](https://mp.weixin.qq.com/s/lwKkLQcfbCNX2W-5SOeZEA)
    * 递归：顺序无所谓，通过递归函数返回值添加节点
    * 迭代：按序遍历，需要记录插入父节点，这样才能做插入操作
* [二叉搜索树中的删除操作](https://mp.weixin.qq.com/s/-p-Txvch1FFk3ygKLjPAKw)
    * 递归：前序，想清楚删除非叶子节点的情况
    * 迭代：有序遍历，较复杂
* [修剪二叉搜索树](https://mp.weixin.qq.com/s/QzmGfYUMUWGkbRj7-ozHoQ)
    * 递归：前序，通过递归函数返回值删除节点
    * 迭代：有序遍历，较复杂
* [构造二叉搜索树](https://mp.weixin.qq.com/s/sy3ygnouaZVJs8lhFgl9mw)
    * 递归：前序，数组中间节点分割
    * 迭代：较复杂，通过三个队列来模拟

## 阶段总结

大家以上题目都做过了，也一定要看如下阶段小结。

**每周小结都会对大家的疑问做统一解答，并且对每周的内容进行拓展和补充，所以一定要看，将细碎知识点一网打尽！**

* [本周小结！（二叉树系列一）](https://mp.weixin.qq.com/s/JWmTeC7aKbBfGx4TY6uwuQ)
* [本周小结！（二叉树系列二）](https://mp.weixin.qq.com/s/QMBUTYnoaNfsVHlUADEzKg)
* [本周小结！（二叉树系列三）](https://mp.weixin.qq.com/s/JLLpx3a_8jurXcz6ovgxtg)
* [本周小结！（二叉树系列四）](https://mp.weixin.qq.com/s/CbdtOTP0N-HIP7DR203tSg)

## 最后总结

**在二叉树题目选择什么遍历顺序是不少同学头疼的事情，我们做了这么多二叉树的题目了，Carl给大家大体分分类**。

* 涉及到二叉树的构造，无论普通二叉树还是二叉搜索树一定前序，都是先构造中节点。

* 求普通二叉树的属性，一般是后序，一般要通过递归函数的返回值做计算。

* 求二叉搜索树的属性，一定是中序了，要不白瞎了有序性了。

注意在普通二叉树的属性中，我用的是一般为后序，例如单纯求深度就用前序， [二叉树：找所有路径](https://mp.weixin.qq.com/s/Osw4LQD2xVUnCJ-9jrYxJA)也用了前序，这是为了方便让父节点指向子节点。

所以求普通二叉树的属性还是要具体问题具体分析。

**最后，二叉树系列就这么完美结束了，估计这应该是最长的系列了，感谢大家33天的坚持与陪伴，接下来我们又要开始新的系列了「回溯算法」！**






## 其他语言版本


Java：


Python：


Go：




-----------------------
* 作者微信：[程序员Carl](https://mp.weixin.qq.com/s/b66DFkOp8OOxdZC_xLZxfw)
* B站视频：[代码随想录](https://space.bilibili.com/525438321)
* 知识星球：[代码随想录](https://mp.weixin.qq.com/s/QVF6upVMSbgvZy8lHZS3CQ)
<div align="center"><img src=../pics/公众号.png width=450 alt=> </img></div>
