#include <iostream>
#include <stack>
#include <queue>
using namespace std;
#define IsRoot(x) (!(x->parent))
#define IsLChild(x) (!IsRoot(x) && (x == x->parent->lChild))
#define IsRChild(x) (!IsRoot(x) && (x == x->parent->rChild))
template <typename DataType>
class BinNode
{
public:
DataType data;
BinNode *lChild,*rChild,*parent;
BinNode():lChild(NULL),rChild(NULL),parent(NULL){};
BinNode<DataType> * succ();
};
template <typename DataType>
BinNode<DataType> * BinNode<DataType>::succ()
{
BinNode<DataType> *node = this;
if(node->rChild)
{
node = node->rChild;
while(node->lChild)
{
node = node->lChild;
}
}else
{
while(IsRChild(node)) node = node->parent;
node = node->parent;
}
return node;
}
template <typename DataType>
class BinTree
{
public:
BinTree() {root = Create();}
BinTree(DataType a[],int n);
~BinTree() {Release(root);}
void preorder_traversal(BinNode<DataType> *binNode); //递归的方式进行前序的遍历
void inorder_traversal(BinNode<DataType> *binNode); //递归的方式进行中序的遍历
void postorder_traversal(BinNode<DataType> *binNode); //递归的方式进行后序的遍历
void levelorder_traversal(BinNode<DataType> *binNode); //层次遍历
void iterative_preorder_traversal(BinNode<DataType> *binNode); //迭代的方式进行前序的遍历版本一
void iterative_preorder_traversal_2(BinNode<DataType> *binNode); //迭代的方式进行前序的遍历版本二
void iterative_inorder_traversal(BinNode<DataType> *binNode); //迭代的方式进行中序的遍历版本一
void iterative_inorder_traversal_2(BinNode<DataType> *binNode); //迭代的方式进行中序的遍历版本二
void iterative_inorder_traversal_3(BinNode<DataType> *binNode); //迭代的方式进行中序的遍历版本三
void iterative_postorder_traversal(BinNode<DataType> *binNode); //迭代的方式进行后序的遍历
BinNode<DataType>* getTheRoot();
private:
BinNode<DataType> *root;
BinNode<DataType> * Create();
void Release(BinNode<DataType> *binNode);
static void VisitAlongLeftBranch(BinNode<DataType> *binNode,stack<BinNode<DataType>* >* s); //static成员函数只能访问static成员,不能访问非static成员
static void GoAlongLeftBranch(BinNode<DataType> *binNode, stack<BinNode<DataType>* > *s);
static void GotoLeft(stack<BinNode<DataType>* > *s);
};
template <typename DataType>
BinNode<DataType>* BinTree<DataType>::Create() //按照先序遍历方式创造二叉树
{
DataType data;
BinNode<DataType> *binNode = NULL;
cout<<"please intput data:"<<endl;
cin>>data;
if(data == -1)
{
binNode = NULL;
return binNode;
}
else
{
binNode = new BinNode<DataType>();
binNode->data = data;
binNode->lChild = Create(); //已经在BinTree<DataType>作用域中,所以不需要再声明在哪个作用域
binNode->rChild = Create();
if(binNode->lChild)
binNode->lChild->parent = binNode;
if(binNode->rChild)
binNode->rChild->parent = binNode;
}
binNode->parent = NULL; //根节点的parent为NULL
return binNode; //返回根节点
}
template <typename DataType>
BinTree<DataType>::BinTree(DataType a[],int len):root(NULL) //按照层次遍历的方式用数组a构造二叉树
{
BinNode<DataType> *binRoot ,*binLeft ,*binRight;
int i = 0;
queue<BinNode<DataType>*> que;
root = new BinNode<DataType>();
root->data = a[0];
root->parent = NULL;
que.push(root);
while(!que.empty() && ++i < len)
{
binRoot = que.front();
que.pop();
binLeft = new BinNode<DataType>();
binLeft->data = a[i];
binRoot->lChild = binLeft;
binLeft->parent = binRoot;
que.push(binLeft);
i++;
if(i >= len) break;
binRight = new BinNode<DataType>();
binRight->data = a[i];
binRoot->rChild = binRight;
binRight->parent = binRoot;
que.push(binRight);
}
}
template <typename DataType>
void BinTree<DataType>::Release(BinNode<DataType> *binNode) //按照后递归将二叉树释放掉
{
if(binNode)
{
Release(binNode->lChild);
Release(binNode->rChild);
delete(binNode);
}
}
template <typename DataType>
void BinTree<DataType>::preorder_traversal(BinNode<DataType> *binNode) //先序递归二叉树
{
if(binNode != NULL)
{
cout<<binNode->data<<'\t';
preorder_traversal(binNode->lChild);
preorder_traversal(binNode->rChild);
}
}
template <typename DataType>
void BinTree<DataType>::inorder_traversal(BinNode<DataType> *binNode) //中序递归二叉树
{
if(binNode->lChild != NULL)
inorder_traversal(binNode->lChild);
cout<<binNode->data<<'/t';
if(binNode->rChild != NULL)
inorder_traversal(binNode->rChild);
}
template <typename DataType>
void BinTree<DataType>::postorder_traversal(BinNode<DataType> * binNode) //后序递归二叉树
{
if(binNode->lChild != NULL)
postorder_traversal(binNode->lChild);
if(binNode->rChild != NULL)
postorder_traversal(binNode->rChild);
cout<<binNode->data<<'/t';
}
template <typename DataType>
void BinTree<DataType>::iterative_preorder_traversal(BinNode<DataType> *binNode) //先序迭代二叉树版本一
{
stack< BinNode<DataType> * > *s = new stack< BinNode<DataType> *>();
if(binNode)
s->push(binNode);
while(!s->empty())
{
binNode = s.pop();
cout<<binNode->data<<'\t';
if(binNode->rChild)
s.push(binNode->rChild);
if(binNode->lChild)
s.push(binNode->lChild);
}
release(s); //动态分配的变量,要记得自己手动释放
}
template <typename DataType>
void BinTree<DataType>::VisitAlongLeftBranch(BinNode<DataType> *binNode, stack< BinNode<DataType>* >* s)
{
while(binNode)
{
cout<<binNode->data<<'\t';
if(binNode->rChild)
s->push(binNode->rChild);
binNode = binNode->lChild;
}
}
template <typename DataType>
void BinTree<DataType>::iterative_preorder_traversal_2(BinNode<DataType> *binNode) //先序迭代遍历二叉树版本二
{
stack< BinNode<DataType> * > *s = new stack< BinNode<DataType> * >();
while(true)
{
BinTree<DataType>::VisitAlongLeftBranch(binNode, s);
if(s->empty())
break;
binNode = s->top();
s->pop();
}
}
template <typename DataType>
void BinTree<DataType>::GoAlongLeftBranch(BinNode<DataType> *binNode, stack< BinNode<DataType>* > *s)
{
while(binNode)
{
s->push(binNode);
binNode = binNode->lChild;
}
}
template <typename DataType>
void BinTree<DataType>::iterative_inorder_traversal(BinNode<DataType> *binNode) //中序迭代遍历二叉树版本一
{
stack< BinNode<DataType>* > *s = new stack< BinNode<DataType>* >();
while(true)
{
BinTree<DataType>::GoAlongLeftBranch(binNode,s);
if(s->empty())
break;
binNode = s->top();
s->pop();
cout<<binNode->data<<'\t';
binNode = binNode->rChild;
}
delete(s); //释放栈
}
template <typename DataType>
void BinTree<DataType>::iterative_inorder_traversal_2(BinNode<DataType> *binNode) //中序迭代遍历二叉树版本二
{
stack< BinNode<DataType>* > *s = new stack< BinNode<DataType>* >();
while(true)
{
if(binNode)
{
s->push(binNode);
binNode = binNode->lChild;
}else if(!s->empty())
{
binNode = s->top();
s->pop();
cout<<binNode->data<<'\t';
binNode = binNode->rChild;
}else
{
delete(s);
break;
}
}
}
template <typename DataType>
void BinTree<DataType>::iterative_inorder_traversal_3(BinNode<DataType> *binNode) //中序迭代遍历二叉树
{
bool backtrack = false;
while(true)
{
if(!backtrack && binNode->lChild)
binNode = binNode->lChild;
else
{
cout<<binNode->data<<'\t';
if(binNode->rChild)
{
binNode = binNode->rChild;
backtrack = false;
}else
{
if(!(binNode = binNode->succ())) break;
backtrack = true;
}
}
}
}
template <typename DataType>
void BinTree<DataType>::GotoLeft(stack<BinNode<DataType>*> *s)
{
BinNode<DataType> *node;
while(node = s->top())
{
if(node->lChild) //尽可能的向左
{
if(node->rChild)
s->push(node->rChild);
s->push(node->lChild);
}else
{
s->push(node->rChild);
}
}
s->pop(); //返回之前,弹出栈顶的空节点
}
template <typename DataType>
void BinTree<DataType>::iterative_postorder_traversal(BinNode<DataType> *binNode) //后序迭代遍历二叉树
{
BinNode<DataType> *top;
stack<BinNode<DataType> *> *s = new stack<BinNode<DataType> *>();
if(binNode)
s->push(binNode);
while(!s->empty())
{
top = s->top();
if(top != binNode->parent) //如果不是其父亲节点,则肯定是其右兄弟。
GotoLeft(s) ; //在以其右兄弟为根之树中进行递归深入其中。
binNode = s->top();
cout<<binNode->data<<'\t';
s->pop();
}
}
template <typename DataType>
void BinTree<DataType>::levelorder_traversal(BinNode<DataType> *binNode) //层次遍历
{
queue<BinNode<DataType>*> que;
que.push(binNode);
while(!que.empty())
{
binNode = que.front();
que.pop();
cout<<binNode->data<<'\t';
if(binNode->lChild)
que.push(binNode->lChild);
if(binNode->rChild)
que.push(binNode->rChild);
}
}
template <typename DataType>
BinNode<DataType>* BinTree<DataType>::getTheRoot() //返回根节点
{
return root; //这里一开始我返回的是*root,导致后面使用栈的时候,如果用数组构造二叉树,那么在后序遍历中push的是形参的BinNode<DataType>的地址,所以这里用指针比较好。。。找了一个小时。。。。
}
void main()
{
int a[10] = {1,2,3,4,5,6,7,8,9,10};
BinTree<int> tree(a,10);
cout<<"the source is: a[10] = {1,2,3,4,5,6,7,8,9,10}"<<endl;
cout<<"the preorder_traversal is:"<<endl;
BinNode<int>* root = tree.getTheRoot();
tree.preorder_traversal(root);
cout<<"the iterative_preorder_traversal_2 is:"<<endl;
root = tree.getTheRoot();
tree.iterative_preorder_traversal_2(root);
cout<<"the iterative_inorder_traversal is:"<<endl;
root = tree.getTheRoot();
tree.iterative_inorder_traversal(root);
cout<<"the iterative_inorder_traversal_2 is:"<<endl;
root = tree.getTheRoot();
tree.iterative_inorder_traversal_2(root);
cout<<"the iterative_inorder_traversal_3 is:"<<endl;
root = tree.getTheRoot();
tree.iterative_inorder_traversal_3(root);
cout<<"the iterative_postorder_traversal is:"<<endl;
root = tree.getTheRoot();
tree.iterative_postorder_traversal(root);
cout<<"the levelorder_traversal is:"<<endl;
root = tree.getTheRoot();
tree.levelorder_traversal(root);
cout<<"please input the source :"<<endl;
BinTree<int> tree1;
cout<<"the preorder_traversal is:"<<endl;
root = tree1.getTheRoot();
tree1.preorder_traversal(root);
cout<<"the iterative_preorder_traversal_2 is:"<<endl;
root = tree1.getTheRoot();
tree1.iterative_preorder_traversal_2(root);
cout<<"the iterative_inorder_traversal is:"<<endl;
root = tree1.getTheRoot();
tree1.iterative_inorder_traversal(root);
cout<<"the iterative_inorder_traversal_2 is:"<<endl;
root = tree1.getTheRoot();
tree1.iterative_inorder_traversal_2(root);
cout<<"the iterative_inorder_traversal_3 is:"<<endl;
root = tree1.getTheRoot();
tree1.iterative_inorder_traversal_3(root);
cout<<"the iterative_postorder_traversal is:"<<endl;
root = tree1.getTheRoot();
tree1.iterative_postorder_traversal(root);
cout<<"the levelorder_traversal is:"<<endl;
root = tree1.getTheRoot();
tree1.levelorder_traversal(root);
}