222. 完全二叉树的节点个数
时间:2020年11月24日
知识点:完全二叉树、二分查找
题目链接:https://leetcode-cn.com/problems/count-complete-tree-nodes/
题目
给出一个完全二叉树,求出该树的节点个数。
说明:
完全二叉树的定义如下:在完全二叉树中,除了最底层节点可能没填满外,其余每层节点数都达到最大值,并且最下面一层的节点都集中在该层最左边的若干位置。若最底层为第 h 层,则该层包含 1~ 2h 个节点。
示例:
输入:
1
/ \
2 3
/ \ /
4 5 6
输出: 6
解法:
- 递归遍历所有节点
- 利用完全二叉树的特点
- 当完全二叉树的高度为x时,最少有 2^x个节点 ,最多2^(x+1)-1个
- 这样就可以先一直找最左的节点确定高度
- 可以用二分法去找 如何判断节点是否存在呢
- 画图可知
1
/ \
2 3
/ \ / \
4 5 6 7
/ \
8 9
- 9这个节点 的二进制位 1001 除了头 每位进行与操作 0:向左 1:向右 可以得到
代码
#include <stdio.h>
#include <iostream>
using namespace std;
struct TreeNode {
int val;
TreeNode *left;
TreeNode *right;
TreeNode(int x) : val(x), left(NULL), right(NULL) {}
};
/*
class Solution {
public:
int countNodes(TreeNode* root) {
if(root==nullptr)return 0;
return countNodes(root->left)+countNodes(root->right)+1;
}
};
*/
class Solution {
public:
int countNodes(TreeNode* root) {
if(root == nullptr)
return 0;
int level = 0;
TreeNode* tmp = root;
while(tmp->left !=nullptr){
level++;
tmp = tmp->left;
}
int left = 1 << level,right = (1 << (level+1)) - 1;
while(left < right){
int mid = (right - left + 1)/2 + left;
if(isexist(root,level,mid))
left = mid;
else
right = mid-1;
}
return left;
}
bool isexist(TreeNode*root,int level,int num){
int tmp = 1 << (level-1);
TreeNode *node = root;
while(node != nullptr && tmp){
if(num & tmp)
node = node->right;
else
node = node->left;
tmp >>= 1;
}
return node!=nullptr;
}
};
class Solution {
public:
int countNodes(TreeNode* root) {
if (root == nullptr) return 0;
TreeNode* left = root->left;
TreeNode* right = root->right;
int leftHeight = 0, rightHeight = 0;
while (left) {
left = left->left;
leftHeight++;
}
while (right) {
right = right->right;
rightHeight++;
}
if (leftHeight == rightHeight)
return (2 << leftHeight) - 1;
return countNodes(root->left) + countNodes(root->right) + 1;
}
};
int main()
{
TreeNode root(1); TreeNode node1(1);
root.left = &node1;
Solution s;
cout<<s.countNodes(&root)<<endl;
return 0;
}
今天也是爱zz的一天哦!