二叉树 完全二叉树节点个数

141 阅读1分钟

题目

求完全二叉树的节点个数

  • 传统的递归遍历能求,下面通过完全二叉树的性质来进行优化
  • 完全二叉树:节点从上到下,从左到右依次排列;满二叉树:除了叶子节点,任意节点的子节点都是满的
  • 如果完全二叉树的右子树的高度+1和整棵树的高度一致,那么左子树一定是满二叉树,可以直接求得答案
  • 如果完全二叉树的右子树高度+1和左子树不一致,那么因为完全二叉树的排列性质,右子树一定是满二叉树,右子树可以求得答案
  • 对于没有直接求得答案的子树,递归需要求解的子树部分(子树也是完全二叉树),根据上面的规律求解
// level:当前节点的深度,height:以当前节点为顶点的完全二叉树的深度
function process(ndoe, level, height) {
  // 只剩一个节点了
  if (level === height) {
    return 1;
  }

  // 如果右树高度和完全二叉树高度一致,左树是个满二叉树,需要求右树完全二叉树高度
  if (getLevel(node.right, level + 1) === height) {
    // 2^(h-level)-1+1
    return (1 << (height - level)) + process(node.right, level + 1, height);
  } else {
    // 如果右树高度不一致,右树是个满二叉树,求左树完全二叉树高度
    return (1 << (height - level - 1)) + process(node.left, level + 1, height);
  }
}

process(node, 1, getLevel(node, 1));

function getLevel(node, level) {
  while (node !== null) {
    level++;
    node = node.left;
  }
  return level - 1;
}