完全二叉树的一些知识
完全二叉树就是在满二叉树的基础上从右往左去若干节点。
判断是否为完全二叉树有两个判断条件,
1.如果左节点为空,而右节点不为空,那么不是完全二叉树。
2.如果层序遍历已经发现了左节点不为空而右节点为空的节点,那么接下来遍历的必须全是叶子节点,否则不是完全二叉树。
满足以上条件就是完全二叉树。(默认空节点也是完全二叉树)
class Solution {
public:
bool isCompleteTree(TreeNode* root) {
bool ok=true;
queue<TreeNode*>p;
p.push(root);
while(p.size())
{
auto t=p.front();
p.pop();
if((!t->left&&t->right)||(!ok&&(t->left||t->right)))
{
return false;
}
if(t->left)p.push(t->left);
if(t->right)p.push(t->right);
if(!t->left||!t->right)
{
ok=false;
}
}
return true;
}
};
O(logn)计算完全二叉树的节点个数
准备一个函数,功能是计算一个树的最大高度,也是一直取非空节点的左节点,同时记录次数即可。
如果一个树的右子树的高度等于大树的高度,说明左子树是满的,那么只需计算右子树。
如果不等于,说明右子树没到最后一层,而是在倒数第二层是满的,那么只需计算左子树。
public static int countNodes(TreeNode head) {
if (head == null) {
return 0;
}
return f(head, 1, mostLeft(head, 1));
}
// cur : 当前来到的节点
// level : 当前来到的节点在第几层
// h : 整棵树的高度,不是cur这棵子树的高度
// 求 : cur这棵子树上有多少节点
public static int f(TreeNode cur, int level, int h) {
if (level == h) {
return 1;
}
if (mostLeft(cur.right, level + 1) == h) {
// cur右树上的最左节点,扎到了最深层
return (1 << (h - level)) + f(cur.right, level + 1, h);
} else {
// cur右树上的最左节点,没扎到最深层
return (1 << (h - level - 1)) + f(cur.left, level + 1, h);
}
}
// 当前节点是cur,并且它在level层
// 返回从cur开始不停往左,能扎到几层
public static int mostLeft(TreeNode cur, int level) {
while (cur != null) {
level++;
cur = cur.left;
}
return level - 1;
}

浙公网安备 33010602011771号