您的位置:首页 > 理论基础 > 数据结构算法

数据结构基础 之 二叉搜索树的思想与实现

2015-07-06 16:22 671 查看
【摘要】

首先,本文阐述二叉搜索树的基本概念,然后,对二叉搜索树的数据结构进行性能分析并给出优化数据结构。最后,贴上了二叉搜索树的创建与遍历的源码。

【正文】

二叉排序树(BinarySortTree)

二叉排序树(BinarySortTree)又称二叉查找树、二叉搜索树。

它或者是一棵空树;或者是具有下列性质的二叉树:

若左子树不空,则左子树上所有结点的值均小于它的根结点的值;若右子树不空,则右子树上所有结点的值均大于它的根结点的值;左、右子树也分别为二叉排序树。

若子树为空,查找不成功。

二叉排序树性能分析

每个结点的C(i)为该结点的层次数。最坏情况下,当先后插入的关键字有序时,构成的二叉排序树蜕变为单支树,树的深度为,其平均查找长度为(n+1)/2(和顺序查找相同),最好的情况是二叉排序树的形态和折半查找的判定树相同,其平均查找长度和log 2 (n)成正比。
二叉排序树优化

***L树、红黑树、Size Balanced Tree(SBT)、Treap(Tree+Heap)这些均可以使查找树的高度为O(log(n))。

【二叉搜索树的创建与遍历源码】

#include <iostream>
using namespace std;
//树结点类的实现
template<class Elem>
class TreeNode
{
public:
<span style="white-space:pre">	</span>TreeNode(Elem dataVal,TreeNode* leftVal     = NULL,TreeNode* rightVal     = NULL)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>data     = dataVal;
<span style="white-space:pre">		</span>left     = leftVal;
<span style="white-space:pre">		</span>right     = rightVal;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>TreeNode(TreeNode* leftVal     = NULL,TreeNode* rightVal     = NULL)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>left     = leftVal;
<span style="white-space:pre">		</span>right     = rightVal;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>TreeNode* GetLeft()
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>return left;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>TreeNode* GetRight()
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>return right;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>Elem GetVal()
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>return data;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>void SetVal(Elem it)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>data     = it;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>void SetLeft(TreeNode<Elem>* l)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>left     = l;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>void SetRight(TreeNode<Elem>* r)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>right     = r;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>TreeNode* left;
<span style="white-space:pre">	</span>TreeNode* right;
<span style="white-space:pre">	</span>Elem data;
};
//树的类型实现。
template<class Elem>
class SearchTree
{
public:
<span style="white-space:pre">	</span>SearchTree(Elem it)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>init(it);
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>~SearchTree()
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>DeleteTree(root);
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>void init(Elem);
<span style="white-space:pre">	</span>void DeleteTree(TreeNode<Elem>*);
<span style="white-space:pre">	</span>void InsertNode(TreeNode<Elem>*,Elem item);
<span style="white-space:pre">	</span>void PreOrder(TreeNode<Elem>*);
<span style="white-space:pre">	</span>bool Find(TreeNode<Elem>*,Elem);
<span style="white-space:pre">	</span>TreeNode<Elem>* GetRoot()
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>return root;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>void InOrder(TreeNode<Elem>* T);
<span style="white-space:pre">	</span>void PostOrder(TreeNode<Elem>* T);
private:
<span style="white-space:pre">	</span>TreeNode<Elem>* root;
};
template<class Elem>
void SearchTree<Elem>::init(Elem item)
{
<span style="white-space:pre">	</span>root     = new TreeNode<Elem>(item,NULL,NULL);
}
template<class Elem>
void SearchTree<Elem>::DeleteTree(TreeNode<Elem>* T)
{
<span style="white-space:pre">	</span>if(T!     = NULL)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>DeleteTree(T->GetLeft());
<span style="white-space:pre">		</span>DeleteTree(T->GetRight());
<span style="white-space:pre">		</span>delete T;
<span style="white-space:pre">	</span>}
}
//插入结点。
template<class Elem>
void SearchTree<Elem>::InsertNode(TreeNode<Elem>* T,Elem item)
{
<span style="white-space:pre">	</span>TreeNode<Elem>* pointer     = NULL;
<span style="white-space:pre">	</span>if(T     =     = NULL)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>init(item);
<span style="white-space:pre">		</span>return;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>else pointer     = T;
<span style="white-space:pre">	</span>while(1)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>if(pointer->GetVal()     =     = item) 
<span style="white-space:pre">			</span>return;
<span style="white-space:pre">		</span>else 
<span style="white-space:pre">			</span>if(pointer->GetVal()>item)
<span style="white-space:pre">			</span>{ 
<span style="white-space:pre">				</span>if(pointer->GetLeft()     =     = NULL)
<span style="white-space:pre">				</span>{
<span style="white-space:pre">					</span>pointer->left     = new TreeNode<Elem>(item,NULL,NULL);
<span style="white-space:pre">					</span>return;
<span style="white-space:pre">				</span>}
<span style="white-space:pre">				</span>else
<span style="white-space:pre">					</span>pointer     = pointer->left;
<span style="white-space:pre">			</span>}
<span style="white-space:pre">			</span>else
<span style="white-space:pre">			</span>{
<span style="white-space:pre">				</span>if(pointer->GetRight()     =     = NULL)
<span style="white-space:pre">				</span>{
<span style="white-space:pre">					</span>pointer->right     = new TreeNode<Elem>(item,NULL,NULL);
<span style="white-space:pre">					</span>return;
<span style="white-space:pre">				</span>}
<span style="white-space:pre">				</span>else
<span style="white-space:pre">					</span>pointer     = pointer->right;
<span style="white-space:pre">			</span>}
<span style="white-space:pre">	</span>}
}
//前序递归遍历。
template<class Elem>
void SearchTree<Elem>::PreOrder(TreeNode<Elem>*T)
{
<span style="white-space:pre">	</span>if(T!     = NULL)
<span style="white-space:pre">		</span>{
<span style="white-space:pre">			</span>cout<<T->GetVal()<<" ";
<span style="white-space:pre">			</span>PreOrder(T->GetLeft());
<span style="white-space:pre">			</span>PreOrder(T->GetRight());
<span style="white-space:pre">		</span>}
}
//二叉递归查找
template<class Elem>
bool SearchTree<Elem>::Find(TreeNode<Elem>* T,Elem item)
{
<span style="white-space:pre">	</span>if(T     =     = NULL)
<span style="white-space:pre">		</span>return false;
<span style="white-space:pre">	</span>else if(T->GetVal()>item)
<span style="white-space:pre">		</span>return  Find(T->left,item);
<span style="white-space:pre">	</span>else if(T->GetVal()<item)
<span style="white-space:pre">		</span>return Find(T->right,item);
<span style="white-space:pre">	</span>else
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>item     = T->GetVal();
<span style="white-space:pre">		</span>return true;
<span style="white-space:pre">	</span>} 
}
//中序递归遍历。
template<class Elem>
void SearchTree<Elem>::InOrder(TreeNode<Elem>*T)
{
<span style="white-space:pre">	</span>if(T!     = NULL)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>InOrder(T->left);
<span style="white-space:pre">		</span>cout<<T->data<<" ";
<span style="white-space:pre">		</span>InOrder(T->right);
<span style="white-space:pre">	</span>}
}
//后序递归遍历。
template<class Elem>
void SearchTree<Elem>::PostOrder(TreeNode<Elem>* T)
{
<span style="white-space:pre">	</span>if(T!     = NULL)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>PostOrder(T->left);
<span style="white-space:pre">		</span>PostOrder(T->right);
<span style="white-space:pre">		</span>cout<<T->data<<" ";
<span style="white-space:pre">	</span>}
}
int main()
{
<span style="white-space:pre">	</span>SearchTree<char> A('h');//先创建一个根结点。
<span style="white-space:pre">	</span>char it;
<span style="white-space:pre">	</span>char item;
<span style="white-space:pre">	</span>TreeNode<char>* b;
<span style="white-space:pre">	</span>b     = A.GetRoot();
<span style="white-space:pre">	</span>cout<<"insert any number in the tree"<<endl;
<span style="white-space:pre">	</span>cout<<"when you enter '# 'is end!"<<endl;
<span style="white-space:pre">	</span>cin>>item;
<span style="white-space:pre">	</span>while(item!     = '#')
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>A.InsertNode(b,item);    //连续插入结点。
<span style="white-space:pre">		</span>cin>>item;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>cout<<"PreOrder print all the number:";
<span style="white-space:pre">	</span>A.PreOrder(b);
<span style="white-space:pre">	</span>cout<<endl;
<span style="white-space:pre">	</span>cout<<"inorder print:";
<span style="white-space:pre">	</span>A.InOrder(b);
<span style="white-space:pre">	</span>cout<<endl;
<span style="white-space:pre">	</span>cout<<" PostOrder print:";
<span style="white-space:pre">	</span>A.PostOrder(b);
<span style="white-space:pre">	</span>cout<<endl;
<span style="white-space:pre">	</span>cin>>it;
<span style="white-space:pre">	</span>if(A.Find(b,it))
<span style="white-space:pre">		</span>cout<<"there is the same number!";
<span style="white-space:pre">	</span>else
<span style="white-space:pre">		</span>cout<<"there isn't the number!";
<span style="white-space:pre">	</span>return 0;
}




【后序遍历判断是否二叉树】
http://blog.csdn.net/pengyan0812/article/details/46409745
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: