C++模板实现的二叉排序树.docx
《C++模板实现的二叉排序树.docx》由会员分享,可在线阅读,更多相关《C++模板实现的二叉排序树.docx(13页珍藏版)》请在冰豆网上搜索。
C++模板实现的二叉排序树
C++模板实现的二叉排序(查找)树
二叉排序树定义:
二叉排序树是这样的树,结点左边的值都小于结点的值,结点右边的值都大于结点的值,所以按照二叉树的中序遍历的话,得到的的将是按顺序排列的值。
二叉排序树的主要操作:
1:
插入
插入的操作非常简单,从根结点开始,如果插入值大于根节点值,则向右遍历,如果小于根节点值,则想左遍历,知道遇到一个叶子结点为止。
按插入值大于叶子则将插入值作为叶子结点的右孩子,否则左孩子。
中间过程中如果遇到跟插入值相等的,则插入失败。
2:
删除
关于有三种情况需要不同对待。
<1>如果是叶子结点,那么直接删除就行(注意相关的孩子指针要变成NULL)。
<2>如果要删除的结点只有左孩子或者右孩子,这样也好办,我们只需要把相应的孩子赋值给待删除结点的双亲结点的孩子指针即可,孙子升级当儿子。
<3>如果要删除的结点既有左孩子,又有右孩子,那么情况就稍微有点麻烦,在这里我们可以采取两种策略来实现,第一种是“前驱不动,移动右孩子法”,第二种是“右孩子不动,移动前驱法”。
具体如下图所示:
3:
遍历
遍历采用递归方法,遍历的实现就很简单了。
4:
清除
在清除树的所有结点的时候,采取了递归思想,判断左孩子是否为空,如果不空则清空做孩子;再判断右孩子是否为空,不为空则清空右孩子;只有当结点左右孩子结点都为空的时候,才释放该结点的空间。
5:
查找
查找要利用二叉排序树的自身优点来进行,每次根据与结点的比较结果选择再继续跟左孩子比较还是跟右孩子比较。
实现代码:
//BSTrees.h
#ifndefDDXX_BSTREES_H
#defineDDXX_BSTREES_H
#include
usingnamespacestd;
template
classBSTrees
{
public:
BSTrees();
~BSTrees();
public:
structNode
{
Typee;
Node*leftChild;
Node*rightChild;
Node()
{
}
Node(Type_e)
{
e=_e;
leftChild=NULL;
rightChild=NULL;
}
};
public:
boolinsert(Typee);
boolerase1(Typee);
boolerase2(Typee);
voidclear();
boolisEmpty();
intgetLength();
Node*find(Typee);
Node*getRoot();
Node*getParent(Node*p);
voidtraverse(Node*ptr);
private:
voidclears(Node*&p);
private:
Node*m_root;
intm_Length;
};
templateBSTrees:
:
BSTrees()
{
m_root=NULL;
m_Length=0;
}
templateboolBSTrees:
:
insert(Typee)
{
Node*ptr=newNode(e);
if(ptr==NULL)
{
cout<<"Allocatememoryfortheelementfailed"<returnfalse;
}
if(m_root==NULL)
{
m_root=ptr;
m_Length++;
returntrue;
}
Node*p=m_root;
Node*pParent=m_root;
while(p!
=NULL)
{
if(e==p->e)
{
cout<<"theelementisalreadyexist"<returnfalse;
}
pParent=p;
if(e>p->e)
{
p=p->rightChild;
}
else
{
p=p->leftChild;
}
}
if(ee)
{
pParent->leftChild=ptr;
}
if(e>pParent->e)
{
pParent->rightChild=ptr;
}
m_Length++;
returntrue;
}
templateboolBSTrees:
:
erase1(Typee)
{
Node*p=find(e);
if(p==NULL)
{
cout<<"There'snothiselementtodelete"<returnfalse;
}
if(p->leftChild==NULL)
{
Node*pParent=getParent(p);
if(pParent->leftChild==p)
pParent->leftChild=p->rightChild;
else
pParent->rightChild=p->rightChild;
deletep;
p=NULL;
m_Length--;
returntrue;
}
if(p->rightChild==NULL)
{
Node*pParent=getParent(p);
if(pParent->leftChild==p)
pParent->leftChild=p->leftChild;
else
pParent->rightChild=p->leftChild;
deletep;
p=NULL;
m_Length--;
returntrue;
}
if(p->leftChild!
=NULL&&p->rightChild!
=NULL)
{
Node*pParent=getParent(p);
Node*pPre=p->leftChild;
Node*ptmp=pPre;
while(pPre->rightChild!
=NULL)
{
ptmp=pPre;
pPre=pPre->rightChild;
}
if(ptmp!
=pPre)
{ptmp->rightChild=pPre->leftChild;
pPre->leftChild=p->leftChild;
pPre->rightChild=p->rightChild;
}
else
pPre->rightChild=p->rightChild;
if(pParent==NULL)
m_root=pPre;
else
if(pParent->leftChild==p)
pParent->leftChild=pPre;
else
pParent->rightChild=pPre;
deletep;
p=NULL;
m_Length--;
returntrue;
}
}
templateboolBSTrees:
:
erase2(Typee)
{
Node*p=find(e);
if(p==NULL)
{
cout<<"There'snothiselementtodelete"<returnfalse;
}
if(p->leftChild==NULL)
{
Node*pParent=getParent(p);
if(pParent->leftChild==p)
pParent->leftChild=p->rightChild;
else
pParent->rightChild=p->rightChild;
deletep;
p=NULL;
m_Length--;
returntrue;
}
if(p->rightChild==NULL)
{
Node*pParent=getParent(p);
if(pParent->leftChild==p)
pParent->leftChild=p->leftChild;
else
pParent->rightChild=p->leftChild;
deletep;
p=NULL;
m_Length--;
returntrue;
}
if(p->leftChild!
=NULL&&p->rightChild!
=NULL)
{
Node*pParent=getParent(p);
Node*ptr=p->leftChild;
while(ptr->rightChild!
=NULL)
ptr=ptr->rightChild;
ptr->rightChild=p->rightChild;
if(pParent==NULL)
m_root=p->leftChild;
else
if(pParent->leftChild==p)
pParent->leftChild=p->leftChild;
else
pParent->rightChild=p->leftChild;
deletep;
p=NULL;
m_Length--;
returntrue;
}
}
templatevoidBSTrees:
:
clear()
{
if(m_root==NULL)
return;
clears(m_root);
m_root=NULL;
}
templatevoidBSTrees:
:
clears(Node*&p)
{
if(p->leftChild!
=NULL)
{
clears(p->leftChild);
p->leftChild=NULL;
}
if(p->rightChild!
=NULL)
{
clears(p->rightChild);
p->rightChild=NULL;
}
deletep;
p=NULL;
m_Length--;
}
templatetypenameBSTrees:
:
Node*BSTrees:
:
getRoot()
{
returnm_root;
}
templateintBSTrees:
:
getLength()
{
returnm_Length;
}
templatetypenameBSTrees:
:
Node*BSTrees:
:
getParent(Node*p)
{
if(p==m_root)
returnNULL;
Node*ptr=m_root;
Node*ptf=ptr;
while(ptr!
=NULL)
{
if(ptr->e==p->e)
returnptf;
if(ptr->e>p->e)
{
ptf=ptr;
ptr=ptr->leftChild;
}
else
{
ptf=ptr;
ptr=ptr->rightChild;
}
}
}
templatetypenameBSTrees:
:
Node*BSTrees:
:
find(Typee)
{
Node*ptr=m_root;
while(ptr!
=NULL)
{
if(ptr->e==e)
returnptr;
if(ptr->e>e)
ptr=ptr->leftChild;
else
ptr=ptr->rightChild;
}
if(ptr==NULL)
returnNULL;
}
templatevoidBSTrees:
:
traverse(Node*ptr)
{
if(ptr==NULL)
return;
if(ptr->leftChild!
=NULL)
traverse(ptr->leftChild);
cout<<"Elementvalue:
"<e<if(ptr->rightChild!
=NULL)
traverse(ptr->rightChild);
}
templateBSTrees:
:
~BSTrees()
{
clear();
}
#endif
//main.cpp
#include
#include"BSTrees.h"
usingnamespacestd;
voidmain()
{
cout<<"************************testBSTreeinsert***********************"<BSTreesBst;
intArr[9]={6,2,8,4,10,0,12,16,14};
for(inti=0;i<9;i++)
Bst.insert(Arr[i]);
Bst.traverse(Bst.getRoot());
cout<<"Tree'slengthis:
"<cout<<"************************testBSTreeerase1***********************"<//Bst.erase1(6);
//Bst.erase1(16);
//Bst.erase1(10);
//Bst.erase1(8);
Bst.erase2(6);
Bst.erase2(16);
Bst.erase2(10);
Bst.erase2(8);
Bst.traverse(Bst.getRoot());
cout<<"Tree'slengthis:
"<Bst.clear();
Bst.traverse(Bst.getRoot());
cout<<"Tree'slengthis:
"<}
测试结果: