二叉搜索树(BST树)的简单实现

 

#include  < stdlib.h >
template
< typename T >
class  CBinSTree;

template 
< typename T >
class  CTreeNode
{//树节点类
public:
    CTreeNode(
const T& item,CTreeNode<T>* lptr = NULL,CTreeNode<T>* rptr = NULL):data(item),left(lptr),right(rptr)
    
{
    }

    CTreeNode
<T>* Left(void)
    
{
        
return left;
    }

    CTreeNode
<T>* Right(void)
    
{
        
return right;
    }

    friend 
class CBinSTree<T>;
public:
    T data;
//数据
private:
    CTreeNode
<T>* left;//左子树
    CTreeNode<T>* right;//右子树
}
;

template
< typename T >
class  CBinSTree  
{//二叉搜索树类
public:
    CBinSTree();
    
virtual ~CBinSTree();
    CBinSTree(
const CBinSTree<T>& tree);
    CBinSTree
<T>& operator = (const CBinSTree<T>& rhs);
    CTreeNode
<T>* FindNode(const T& item,CTreeNode<T>* &parent)const;//寻找节点
    void PrintTree();//前序遍历树(非递归)
    void ClearTree();//清空树
    void Insert(const T& item);//插入数据
    void Delete(const T& item);//删除数据
    bool Contains(const T& item);//是否包含数据
    CTreeNode<T>* FindMin()const;//找最小值
    CTreeNode<T>* FindMax()const;//找最大值

protected:
    
//辅助函数区
    CTreeNode<T>* GetTreeNode(const T& item,CTreeNode<T>* lptr=NULL,CTreeNode<T>* rptr=NULL);//分配树节点
    void FreeTreeNode(CTreeNode<T>* p);//释放树节点
    void DeleteTree(CTreeNode<T>* t);//删除树
    CTreeNode<T>* CopyTree(CTreeNode<T>* t);//拷贝树
private:
    CTreeNode
<T> *root;//二叉搜索树树根
    int size;//树节点个数
}
;

 

#include  " stdafx.h "
#include 
" BinSTree.h "
#include 
< iostream >
#include 
< stack >
using   namespace  std;

//
//  Construction/Destruction
//
template < typename T >
CBinSTree
< T > ::CBinSTree()
{
    
this->root = NULL;
    
this->size = 0;
}

template
< typename T >
CBinSTree
< T > ::CBinSTree( const  CBinSTree < T >&  tree)
{
    root 
= this->CopyTree(tree.root);
    
this->size = tree.size;
}

template
< typename T >
CBinSTree
< T > :: ~ CBinSTree()
{
    
this->ClearTree();
}

template
< typename T >
CBinSTree
< T >&  CBinSTree < T > :: operator   =  ( const  CBinSTree < T >&  rhs)
{
    
if(this==&rhs)
        
return *this;
    
this->ClearTree();
    root 
= this->CopyTree(rhs.root);
    size 
= rhs.size;
    
return *this;
}

template
< typename T >
CTreeNode
< T >*  CBinSTree < T > ::GetTreeNode( const  T &  item,CTreeNode < T >*  lptr,CTreeNode < T >*  rptr)
{
    CTreeNode
<T>* p;
    p 
= new CTreeNode<T>(item,lptr,rptr);
    
if(p==NULL)
    
{
        cerr
<<"分配内存失败!"<<endl;
        exit(
1);
    }

    
return p;
}

template
< typename T >
CTreeNode
< T >*  CBinSTree < T > ::FindMin() const
{
    CTreeNode
<T> *= root;
    
while(t->left!=NULL)
    
{
        t 
= t->left;
    }

    
return t;
}

template
< typename T >
CTreeNode
< T >*  CBinSTree < T > ::FindMax() const
{
    CTreeNode
<T> *= root;
    
while(t->right!=NULL)
    
{
        t 
= t->right;
    }

    
return t;
}

template
< typename T >
bool  CBinSTree < T > ::Contains( const  T &  item)
{
    CTreeNode
<T> *p;
    
return (this->FindNode(item,p)!=NULL);
}

template
< typename T >
CTreeNode
< T >*  CBinSTree < T > ::CopyTree(CTreeNode < T >*  t)
{
    CTreeNode
<T> *newnode,*newlptr,*newrptr;
    
if(t==NULL)
        
return NULL;
    
if(t->Left()!=NULL)
        newlptr 
= CopyTree(t->Left());
    
else
        newlptr 
= NULL;
    
if(t->Right()!=NULL)
        newrptr 
= CopyTree(t->Right());
    
else
        newrptr 
= NULL;
    newnode 
= GetTreeNode(t->data,newlptr,newrptr);
    
return newnode;
}

template
< typename T >
void  CBinSTree < T > ::FreeTreeNode(CTreeNode < T >*  p)
{
    delete p;
    p 
= NULL;
}

template
< typename T >
void  CBinSTree < T > ::DeleteTree(CTreeNode < T >*  t)
{
    
if(t!=NULL)
    
{
        DeleteTree(t
->Left());
        DeleteTree(t
->Right());
        FreeTreeNode(t);
    }

}

template
< typename T >
void  CBinSTree < T > ::ClearTree()
{
    DeleteTree(root);
    root 
= NULL;
}

template
< typename T >
CTreeNode
< T >*  CBinSTree < T > ::FindNode( const  T &  item,CTreeNode < T >*   & parent) const
{
    CTreeNode
<T> *= root;
    parent 
= NULL;
    
while(t!=NULL)
    
{
        
if(item==t->data)
            
break;
        
else
        
{
            parent 
= t;
            
if(item<t->data)
                t 
= t->Left();
            
else 
                t 
= t->Right();
        }

    }

    
return t;
}

template
< typename T >
void  CBinSTree < T > ::Insert( const  T &  item)
{
    CTreeNode
<T>* t = root,*parent = NULL,*newnode;
    
while(t!=NULL)
    
{
        parent 
= t;
        
if(item<t->data)
            t 
= t->Left();
        
else
            t 
= t->Right();
    }

    newnode 
= this->GetTreeNode(item);
    
if(parent==NULL)
        root 
= newnode;
    
else if(item<parent->data)
        parent
->left = newnode;
    
else
        parent
->right = newnode;
    size
++;
}

template
< typename T >
void  CBinSTree < T > ::Delete( const  T &  item)
{
    CTreeNode
<T> *pDNode,*pRNode,*pParNode;
    
if((pDNode = this->FindNode(item,pParNode))==NULL)
        
return;
    
if(pDNode->left==NULL)
        pRNode 
= pDNode->right;
    
else if(pDNode->right==NULL)
        pRNode 
= pDNode->left;
    
else
    
{
        CTreeNode
<T> *pParOfRNode = pDNode;
        pRNode 
= pDNode->left;
        
while(pRNode->right!=NULL)
        
{
            pParOfRNode 
= pRNode;
            pRNode 
= pRNode->right;
        }

        
if(pParOfRNode==pDNode)
        
{
            pRNode
->right = pDNode->right;
        }

        
else
        
{
            pParOfRNode
->right = pRNode->left;
            pRNode
->left = pDNode->left;
            pRNode
->right = pDNode->right;
        }

    }

    
if(pParNode==NULL)
        root 
= pRNode;
    
else if(pDNode->data<pParNode->data)
        pParNode
->left = pRNode;
    
else
        pParNode
->right = pRNode;
    
this->FreeTreeNode(pDNode);
    
this->size--;

}

template
< typename T >
void  CBinSTree < T > ::PrintTree()
{
    stack
<CTreeNode<T>* > s;
    CTreeNode
<T>* p = root;
    
while (p!=NULL || !s.empty())
    
{
        
while (p!=NULL)             //遍历左子树
        {
            cout
<<p->data<<endl;
            s.push(p);
            p
=p->Left();
        }
//endwhile
        
        
if (!s.empty())
        
{
            p
=s.top();
            s.pop();
            p
=p->Right();            //通过下一次循环实现右子树遍历
        }
//endif   
    }

}

 

//  test.cpp : Defines the entry point for the console application.
//

#include 
" stdafx.h "
#include 
" BinSTree.cpp "
#include 
< iostream >
using   namespace  std;

CBinSTree
< int >*  MakeSampleTree()
{//示例BST树
    CBinSTree<int> *tree1 = new CBinSTree<int>();
    
int a = 5;
    tree1
->Insert(a);
    tree1
->Insert(30);
    tree1
->Insert(65);
    tree1
->Insert(25);
    tree1
->Insert(35);
    tree1
->Insert(50);
    tree1
->Insert(10);
    tree1
->Insert(28);
    tree1
->Insert(26);
    tree1
->Insert(33);
    
return tree1;
}


int  main( int  argc,  char *  argv[])
{
    CBinSTree
<int> *tree1 = MakeSampleTree();
    tree1
->PrintTree();
    std::cout
<<"删除节点30:"<<endl;
    tree1
->Delete(30);
    tree1
->PrintTree();
    cout
<<tree1->Contains(40)<<endl;
    CTreeNode
<int> *= tree1->FindMin();
    cout
<<p->data<<endl;
    
return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值