#pragma once
#include <iostream>
#include <string>
#include <queue>
#include <stack>
using namespace std;
template<class T>
struct BiNode
{
T data;
BiNode* left,*right;
BiNode():left(NULL),right(NULL){};
BiNode(const T& item,BiNode<T>* lptr=NULL,BiNode<T>* rptr=NULL)
:data(item),left(lptr),right(rptr){}
};
template<class T>
class BinaryTree
{
//friend ostream& operator<<(ostream& out,BinaryTree<T> &_root);
public:
BinaryTree();
BinaryTree(const BinaryTree<T>& _root);
void PreorderTraverse();//先序遍历二叉树
void InorderTraverse();//中序遍历二叉树
void PostorderTraverse();//后序遍历二叉树
void LevelorderTraverse();//层次遍历二叉树
void countLeaf(int &count);//统计二叉树中的叶节点数
void nonRecursivePreOrder();
void nonRecursiveInOrder();
void nonRecursivePostOrder();
int depth();//计算树的深度
~BinaryTree();
private:
BiNode<T>* root;
BiNode<T>* copyTree(BiNode<T>* t);//复制二叉树
void deleteTree(BiNode<T>* t);//删除二叉树
void preTraverse(BiNode<T>* _root);
void inTraverse(BiNode<T>* _root);
void postTraverse(BiNode<T>* _root);
void countLeafNum(BiNode<T>* _root,int &count);
int treeDepth(BiNode<T>* _root);
};
template<class T>
BinaryTree<T>::BinaryTree():root(NULL)
{
BiNode<T> *b,*c,*d,*e,*f,*g,*h,*i;
T _item;
cout<<"Please input the value of Node g:";
cin>>_item;
g=new BiNode<T>(_item);
cout<<"Please input the value of Node h:";
cin>>_item;
h=new BiNode<T>(_item);
cout<<"Please input the value of Node i:";
cin>>_item;
i=new BiNode<T>(_item);
cout<<"Please input the value of Node d:";
cin>>_item;
d=new BiNode<T>(_item,(BiNode<T>*)NULL,g);
cout<<"Please input the value of Node e:";
cin>>_item;
e=new BiNode<T>(_item,h,i);
cout<<"Please input the value of Node f:";
cin>>_item;
f=new BiNode<T>(_item);
cout<<"Please input the value of Node b:";
cin>>_item;
b=new BiNode<T>(_item,d,(BiNode<T>*)NULL);
cout<<"Please input the value of Node c:";
cin>>_item;
c=new BiNode<T>(_item,e,f);
cout<<"Please input the value of Node root:";
cin>>_item;
root=new BiNode<T>(_item,b,c);
}
template<class T>
BiNode<T>* BinaryTree<T>::copyTree(BiNode<T> *_root)
{
BiNode<T>* newLeft,*newRight,*newRoot;
if(_root==NULL)
return NULL;
newLeft=copyTree(_root->left);
newRight=copyTree(_root->right);
newRoot=new BiNode<T>(_root->data,newLeft,newRight);
return newRoot;
}
template<class T>
BinaryTree<T>::BinaryTree(const BinaryTree<T> &_root)
{
root=copyTree(_root.root);
}
template<class T>
void BinaryTree<T>::deleteTree(BiNode<T> *_root)
{
if(_root!=NULL)
{
deleteTree(_root->left);
deleteTree(_root->right);
delete _root;
}
}
template<class T>
BinaryTree<T>::~BinaryTree()
{
deleteTree(root);
}
template<class T>
void BinaryTree<T>::preTraverse(BiNode<T>* _root)
{
if(_root!=NULL)
{
cout<<_root->data<<"——>";
preTraverse(_root->left);
preTraverse(_root->right);
}
}
template<class T>
void BinaryTree<T>::inTraverse(BiNode<T>* _root)
{
if(_root!=NULL)
{
inTraverse(_root->left);
cout<<_root->data<<"——>";
inTraverse(_root->right);
}
}
template<class T>
void BinaryTree<T>::postTraverse(BiNode<T>* _root)
{
if(_root!=NULL)
{
postTraverse(_root->left);
postTraverse(_root->right);
cout<<_root->data<<"——>";
}
}
template<class T>
void BinaryTree<T>::PreorderTraverse()
{
preTraverse(root);
}
template<class T>
void BinaryTree<T>::InorderTraverse()
{
inTraverse(root);
}
template<class T>
void BinaryTree<T>::PostorderTraverse()
{
postTraverse(root);
}
template<class T>
void BinaryTree<T>::LevelorderTraverse()
{
queue<BiNode<T> *> q;
BiNode<T>* p;
q.push(root);
while(!q.empty())
{
p=q.front();
q.pop();
cout<<p->data<<"——>";
if(p->left!=NULL)
q.push(p->left);
if(p->right!=NULL)
q.push(p->right);
}
}
template<class T>
void BinaryTree<T>::countLeafNum(BiNode<T> *_root,int &count)
{
if(_root!=NULL)
{
if(_root->left==NULL&&_root->right==NULL)
count++;
countLeafNum(_root->left,count);
countLeafNum(_root->right,count);
}
}
template<class T>
void BinaryTree<T>::countLeaf(int &count)
{
countLeafNum(root,count);
}
template<class T>
int BinaryTree<T>::treeDepth(BiNode<T> *_root)
{
int depthleft,depthright,depthval;
if(_root==NULL)
depthval=-1;
else
{
depthleft=treeDepth(_root->left);
depthright=treeDepth(_root->right);
depthval=1+(depthleft>depthright?depthleft:depthright);
}
return depthval;
}
template<class T>
int BinaryTree<T>::depth()
{
return treeDepth(root);
}
template<class T>
void BinaryTree<T>::nonRecursivePreOrder()
{
stack<BiNode<T> *> sNode;
BiNode<T> *q,*p=root;
if(p!=NULL)
{
cout<<p->data<<"——>";
sNode.push(p);
}
p=p->left;
while (!sNode.empty()||p!=NULL )
{
while(p!=NULL)
{
cout<<p->data<<"——>";
sNode.push(p);
p=p->left;
}
if(!sNode.empty())
{
q=sNode.top();
sNode.pop();
p=q->right;
}
}
}
template<class T>
void BinaryTree<T>::nonRecursiveInOrder()
{
stack<BiNode<T> *> sNode;
BiNode<T> *p=root,*q;
if(p!=NULL)
sNode.push(p);
p=p->left;
while(!sNode.empty()||p!=NULL)
{
while(p!=NULL)
{
sNode.push(p);
p=p->left;
}
if(!sNode.empty())
{
q=sNode.top();
sNode.pop();
cout<<q->data<<"——>";
p=q->right;
}
}
}
template<class T>
void BinaryTree<T>::nonRecursivePostOrder()
{
stack<BiNode<T> *> sNode;
BiNode<T> *p=root,*q,*pre=NULL;
if(p!=NULL)
sNode.push(p);
p=p->left;
while(!sNode.empty()||p!=NULL)
{
while(p!=NULL)
{
sNode.push(p);
p=p->left;
}
if(!sNode.empty())
{
q=sNode.top();
p=q->right;
if(p==NULL||p==pre)
{
cout<<q->data<<"——>";
sNode.pop();
pre=q;
p=NULL;
}
}
}
}