题目:求二叉树叶子节点的个数/求二叉树第k层的节点个数
二叉树如图所示:
#pragma once
#include<stdlib.h>
#include<queue>
#include<stack>
#include<iostream>
using namespace std;
template<class T>
struct BinaryTreeNode //创建树中的每个结点
{
BinaryTreeNode(const T& data)
:_data(data)
,_pLeft(NULL)
,_pRight(NULL)
{}
T _data; //结点的值
BinaryTreeNode<T>* _pLeft; //左孩子
BinaryTreeNode<T>* _pRight; //右孩子
};
template<class T>
class BinaryTree
{
typedef BinaryTreeNode<T> Node;
public:
BinaryTree()
:_pRoot(NULL)
{}
//构造函数
BinaryTree(const T array[], size_t size, const T& invalid) //按照前序遍历创建一棵树
{
//创建树 ->根结点->左子树->右子树
size_t index = 0; //引用要被初始化
_CreateTree(_pRoot, array, size, invalid, index);
}
//拷贝构造函数--按照前序遍历再创建一棵树
BinaryTree(const BinaryTree<T>& t)
{
_pRoot = _CopyBinaryTree(t._pRoot);
}
//赋值--拷贝一个一样的树
BinaryTree<T>& operator=(const BinaryTree<T>& t)
{
if (this != &t)
{
_DestroyTree(_pRoot);
_pRoot = _CopyBinaryTree(t._pRoot);
}
return *this;
}
//先序遍历
void PreOrder()
{
cout << "PreOrder: " << endl;
_PreOrder(_pRoot);
cout << endl;
}
//求二叉树叶子节点的个数
size_t GetLeefNode()
{
return _GetLeefNode(_pRoot);
}
//求二叉树第k层的节点个数
size_t GetKLevelNode(size_t k)
{
return _GetKLevelNode(_pRoot, k);
}
//获取二叉树的高度
size_t Height()
{
return _Height(_pRoot);
}
~BinaryTree()
{
_DestroyTree(_pRoot);
}
private:
void _CreateTree(Node *& pRoot, const T array[], size_t size, const T& invalid, size_t& index)
//Node *& pRoot是因为_pRoot已经是一个指针了,需要二级指针或一级指针的引用接收
//因为结点的index是需要被带回的,所以为了改变外部实参要传引用
{
if ((index < size) && (array[index] != invalid)) //index<size条件在前先保证index不越界
{
//1)、创建根结点
pRoot = new Node(array[index]);
//2)、创建根结点的左子树
_CreateTree(pRoot->_pLeft, array , size, invalid, ++index);
//3)、创建根结点的右子树
_CreateTree(pRoot->_pRight, array, size, invalid, ++index);//递归后退时index的值未发生改变
}
} //O(2n+1)->O(n)
Node* _CopyBinaryTree(Node* pRoot)
{
Node* pNewNode = NULL;
if (NULL != pRoot)
{
Node* pNewNode = new Node(pRoot->_data);
pNewNode->_pLeft = _CopyBinaryTree(pRoot->_pLeft);
pNewNode->_pRight = _CopyBinaryTree(pRoot->_pRight);
}
return pNewNode;
}
void _DestroyTree(Node*& pRoot)
{
if (pRoot)
{
_DestroyTree(pRoot->_pLeft);
_DestroyTree(pRoot->_pRight);
delete pRoot;
pRoot = NULL;
}
}
void _PreOrder(Node* pRoot) //先序遍历:根-左子树-右子树
{
if (pRoot)
{
cout << pRoot->_data << " ";
//遍历左子树
_PreOrder(pRoot->_pLeft);
//遍历右子树
_PreOrder(pRoot->_pRight);
}
}
//求二叉树叶子节点的个数
size_t _GetLeefNode(Node* pRoot)
{
if (NULL == pRoot) //空的二叉树
return 0;
if (NULL == pRoot->_pLeft && NULL == pRoot->_pRight) //二叉树只有根节点存在
return 1;
return ((_GetLeefNode(pRoot->_pLeft)) + (_GetLeefNode(pRoot->_pRight))); //左子树的叶子节点+右子树的叶子节点
}
//求二叉树第k层的节点个数
size_t _GetKLevelNode(Node* pRoot, size_t k)
{
if (NULL == pRoot || k < 1 || k > _Height(pRoot)) //检测K的合法性,是否在树中
return 0;
if (1 == k) //第1层
return 1;
size_t leftcount = _GetKLevelNode(pRoot->_pLeft, k-1); //第k-1层
size_t rightcount = _GetKLevelNode(pRoot->_pRight, k-1);
return (leftcount+rightcount);
}
//获取二叉树的高度
size_t _Height(Node* pRoot)
{
if (NULL == pRoot)
return 0; //空树--高度h=0
if (NULL == pRoot->_pLeft && NULL == pRoot->_pRight)
return 1; //只有根节点---h=1
size_t leftHeight = _Height(pRoot->_pLeft); //获取左子树的高度
size_t rightHeight = _Height(pRoot->_pRight); //获取右子树的高度
return (leftHeight > rightHeight)? (leftHeight+1):(rightHeight+1);
}
private:
BinaryTreeNode<T>* _pRoot;
};
void FunTest()
{
const char* pstr = "124###35##6";
BinaryTree<char> t(pstr, strlen(pstr), '#');
BinaryTree<char> t1(t);
BinaryTree<char> t2;
t2 = t;
cout << t.GetLeefNode() << endl;
cout << t.GetKLevelNode(2) << endl;
}
结果如图所示: