力扣-222-完全二叉树的节点个数-javaScript实现

一:递归版

这道题利用后序遍历会容易些 为什么呐? 因为他需要收集左右孩子的节点并且返回给中间的节点

 另外不要忘了 递归三部曲 1.确定返回值和参数 2.终止条件 3.单层判断的逻辑

var countNodes = function(root) {
    // 1. 确定返回值和参数
    let getNumbers = function(node){
        // 2.判断终止条件
        if(node === null)return 0;
        //单层逻辑的判断
        let leftNum = getNumbers(node.left); // 左
        let rightNum = getNumbers(node.right); // 右
        let sumNum = leftNum + rightNum + 1;  // 中  这里+1 就是为了加上中间的节点
        return sumNum;
    }
    return getNumbers(root)
};

二:迭代版(层序遍历)

// 迭代(层序遍历)版本 跟二叉树的层序遍历很相近
var countNodes = function(root) {
    if(root === null)return 0;
    // 利用队列来实现 
    let queue = [];
    queue.push(root);
    // 定义节点个数变量
    let nodeNum = 0;
    while(queue.length){
        // 记录此时队列里面的元素长度 因为后序queue里面的长度在随时变化
        let length = queue.length
        while(length--){
            // 这里面就是对每一层节点的操作
            nodeNum++; // 记录每一层节点的个数
            let node = queue.shift(); // 将队列中每一层的节点都记录并释放出来
            // 进入下一层
             node.left && queue.push(node.left)
             node.right && queue.push(node.right)
        }
    }
    return nodeNum;
}

三:利用完全二叉树特性求解

        利用完全二叉树的特性来求解(对完全二叉树不理解的话 可以看一下前面的那个二叉树的理论基础)  也就是找满二叉树 如果整个大树不是满二叉树的话 就往子树去寻找

        如果找到满二叉树的话就不用去按个遍历节点 直接利用公式 2的n次方-1 这里的n指的是二叉树的深度 所以在这之前要去确定二叉树的深度

          这里利用的是递归来求解 判断是否为二叉树 就要求 左右子树的深度是一样的

let countNodes = function(root){
    if(root === null)return 0;
    // 终止条件
    let left = root.left;
    let right = root.right;
    // 记录左子树的深度和右子树的深度
    let leftDeep = 0,rightDeep = 0;
    while(left){
        left = left.left;
        leftDeep++;
    }
    while(right){
        right = right.right
        rightDeep++;
    }
    // 如果左子树深度和右子树深度一样的话 就利用满二叉树公式2的n次方 - 1来求解(n为子树的深度)
    if(leftDeep === rightDeep){
        // 直接返回公式计算出来的值
        return Math.pow(2, leftDeep + 1) - 1
    }

    // 递归 判断单层逻辑
    let leftNum = countNodes(root.left)
    let rightNum = countNodes(root.right)

    return leftNum + rightNum + 1
}

 可以直接在力扣上编译运行的代码

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值