• 是一种常用的数据结构,用来模拟具有树状结构性质的数据集合
    • 树的每一个节点有一个根植和一个包含所有子节点的列表。
  • 二叉树

    • 二叉树是一种更为典型的树状结构。二叉树每个节点最多具有两个子树,通常子树称为“左子树”和“右子树”
  • 二叉树前序遍历

    • 前序遍历首先访问根节点,然后遍历左子树,最后遍历右子树(根节点 -> 左子树 -> 右子树)
    • 算法:
/**
* Definition for a binary tree node.
* function TreeNode(val) {
*     this.val = val;
*     this.left = this.right = null;
* }
*/
/**
* @param {TreeNode} root
* @return {number[]}
*/

//  递归
const preorderTraversal = function(root) {
   let result = []
   function fn(root){
       if(root !== null){
           result.push(root.val)
           if(root.left) fn(root.left)
           if(root.right) fn(root.right)
       }
   }
   fn(root)
   return result
};
  • 二叉树中序遍历
    • 先遍历左子树,然后访问根节点,最后遍历右子树(左子树 -> 根节点 -> 右子树)
    • 算法:
/**
 * Definition for a binary tree node.
 * function TreeNode(val) {
 *     this.val = val;
 *     this.left = this.right = null;
 * }
 */
/**
 * @param {TreeNode} root
 * @return {number[]}
 */

const inorderTraversal = function(root) {
    let result = []
    function fn(root){
        if(root !== null){
            if(root.left) fn(root.left)
            result.push(root.val)
            if(root.right) fn(root.right)
        }
    }
    fn(root)
    return result
};
  • 二叉树后序遍历
    • 先遍历左子树,然后遍历右子树,最后访问根节点(左子树 -> 右子树 -> 根节点)
    • 算法
/**
 * Definition for a binary tree node.
 * function TreeNode(val) {
 *     this.val = val;
 *     this.left = this.right = null;
 * }
 */
/**
 * @param {TreeNode} root
 * @return {number[]}
 */
const postorderTraversal = function(root) {
    let result = []
    function fn(root){
        if(root !== null){
            if(root.left) fn(root.left)
            if(root.right) fn(root.right)
            result.push(root.val)
        }
    }
    fn(root)
    return result
};
  • 二叉树层序遍历
    • 算法:
/**
 * Definition for a binary tree node.
 * function TreeNode(val) {
 *     this.val = val;
 *     this.left = this.right = null;
 * }
 */
/**
 * @param {TreeNode} root
 * @return {number[][]}
 */

// 广度优先 前序
const levelOrder = function(root) {
    let levels = []
    if(root === null) return levels
    function fn(node, level){
        let len = levels.length
        if(len === level) levels.push([]) 
        levels[level].push(node.val)
        if(node.left) fn(node.left, level+1)
        if(node.right) fn(node.right, level+1)
    }
    fn(root, 0)
    return levels
};
  • 二叉树最大深度
    • 给定一个二叉树,找出其最大深度。二叉树的深度为根节点到最远叶子节点的最长路径上的节点数
    • 算法:
/**
 * Definition for a binary tree node.
 * function TreeNode(val) {
 *     this.val = val;
 *     this.left = this.right = null;
 * }
 */
/**
 * @param {TreeNode} root
 * @return {number}
 */
var maxDepth = function(root) {
    // 写递归的一个重要思路就是相信这个函数能完成任务,此题带有动态规划的感觉
    // 最大深度 = 1+Math.max(根节点的左子树最大深度, 根节点的右子树最大深度)
    // 根节点的左子树最大深度 = 1 + Math.max(左子树的左子树最大深度, 左子树的右子树最大深度)
    // 根节点的右子树最大深度 = 1 + Math.max(右子树的左子树最大深度, 右子树的右子树最大深度)
    if(!root){
        return 0
    }else{
        return Math.max(maxDepth(root.left), maxDepth(root.right)) + 1
    }
};
  • 对称二叉树
    • 给定一个二叉树,检查它是否是镜像对称的。
    • 算法:
/**
 * Definition for a binary tree node.
 * function TreeNode(val) {
 *     this.val = val;
 *     this.left = this.right = null;
 * }
 */
/**
 * @param {TreeNode} root
 * @return {boolean}
 */
var isSymmetric = function(root) {
    return isMirroTree(root, root)
};

function isMirroTree(root_1, root_2){
    if(root_1 === null && root_2 === null) return true
    if(root_1 === null || root_2 === null) return false
    return (root_1.val === root_2.val) && isMirroTree(root_1.left, root_2.right) && isMirroTree(root_1.right, root_2.left)
}
  • 路径总和
    • 给定一个二叉树和一个目标和,判断该树中是否存在根节点到叶子节点的路径,这条路径上所有节点值相加等于目标和。
    • 说明: 叶子节点是指没有子节点的节点。
    • 算法:
/**
 * Definition for a binary tree node.
 * function TreeNode(val) {
 *     this.val = val;
 *     this.left = this.right = null;
 * }
 */
/**
 * @param {TreeNode} root
 * @param {number} sum
 * @return {boolean}
 */
var hasPathSum = function(root, sum) {
    return helper(root, sum)
};

function helper(node, sum){
    if(!node){
        return false
    }else{
        sum -= node.val
    }
    if(!node.left && !node.right){
        return sum === 0
    }
    return helper(node.left, sum) || helper(node.right, sum)
}