1、二叉排序树(BST)的定义
二叉排序树(Binary Sort Tree或Binary Search Tree) BST的定义为:
二叉排序树或者是空树,或者是满足下列性质的二叉树。
(1) :若左子树不为空,则左子树上所有结点的值(关键字)都小于根结点的值;
(2) :若右子树不为空,则右子树上所有结点的值(关键字)都大于根结点的值;
(3) :左、右子树都分别是二叉排序树。
结论:若按中序遍历一棵二叉排序树,所得到的结点序列是一个递增序列
2、BST树的查找
首先将给定的K值与二叉排序树的根结点的关键字进行比较:若相等:则查找成功;
① 给定的K值小于BST的根结点的关键字:继续在该结点的左子树上进行查找;
② 给定的K值大于BST的根结点的关键字:继续在该结点的右子树上进行查找
3、BST树的插入
在BST树中插入一个新结点,要保证插入后仍满足BST的性质。
插入思想
在BST树中插入一个新结点x时,若BST树为空,则令新结点x为插入后BST树的根结点;否则,将结点x的关键字与根结点T的关键字进行比较:
① 若相等: 不需要插入;
② 若x.keykey:结点x插入到T的左子树中;
③ 若x.key>T->key:结点x插入到T的右子树中。
4、BST树的删除
删除操作过程分析
从BST树上删除一个结点,仍然要保证删除后满足BST的性质。设被删除结点为p,
其父结点为f ,删除情况如下:
① 若p是叶子结点: 直接删除p,如图所示。
② 若p只有一棵子树(左子树或右子树):直接用p的左子树(或右子树)取代p的位
置而成为f的一棵子树。即原来p是f的左子树,则p的子树成为f的左子树;原
来p是f的右子树,则p的子树成为f的右子树,如图©、 (d)所示。
③ 若p既有左子树又有右子树 :处理方法有以下两种,可以任选其中一种。
◆ 用p的直接前驱结点代替p。即从p的左子树中选择值最大的结点s放在p的
位置(用结点s的内容替换结点p内容),然后删除结点s。s是p的左子树中的
最右边的结点且没有右子树,对s的删除同②,如图(e)所示。
◆ 用p的直接后继结点代替p。即从p的右子树中选择值最小的结点s放在p的
位置(用结点s的内容替换结点p内容),然后删除结点s。s是p的右子树中的
最左边的结点且没有左子树,对s的删除同②,如图(f)所示。
5、性能分析
》 每个结点的C(i)为该结点的层次数。
》 最坏情况下,当先后插入的关键字有序时,构成的二叉排序树蜕变为
单支树,树的深度为其平均查找长度(n+1)/2(和顺序查找相同),最
好的情况是二叉排序树的形态和折半查找的判定树相同,其平均查找
长度和log 2 (n)成正比
6、BST树的操作代码实现
#include <iostream>
#include <cstdlib>
#include <cstring>
#include <stack>
#include <queue>
using namespace std;
typedef struct node{
int item;
struct node *lchild;
struct node *rchild;
}BSTNode;
BSTNode *root = NULL;
//创建节点
BSTNode *mk_node(int item)
{
BSTNode *p = (BSTNode *)malloc(sizeof(BSTNode));
if(p == NULL)
{
cout << "malloc failed!" << endl;
exit(1);
}
p->item = item;
p->lchild = NULL;
p->rchild = NULL;
return p;
}
//创建BST树(插入节点)//递归
void insert_node(BSTNode *current, BSTNode *p)
{
if(p->item > current->item)
{
if(current->rchild == NULL)
{
current->rchild = p;
}else
{
insert_node(current->rchild, p);
}
}else if(p->item < current->item)
{
if(current->lchild == NULL)
{
current->lchild = p;
}else
{
insert_node(current->lchild, p);
}
}else
{
free(p);
}
}
void create_BST(int item)
{
BSTNode *p = mk_node(item);
if(root == NULL)
{
root = p;
}else
{
insert_node(root, p);
}
}
//创建BST树(插入节点)//迭代
void create_BST_r(int item)
{
BSTNode *pre = NULL;
BSTNode *parent = NULL;
BSTNode *p = mk_node(item);
pre = parent = root;
if(root == NULL)
{
root = p;
return;
}
while(pre != NULL)
{
parent = pre;
if(item > pre->item)
{
pre = pre->rchild;
}else if(item < pre->item)
{
pre = pre->lchild;
}else
{
free(p);
return;
}
}
if(item > parent->item)
parent->rchild = p;
else
parent->lchild = p;
}
/*---------------------三种递归遍历----------------------*/
//先序遍历
void prePrint_o(BSTNode *p)
{
if(p == NULL)
return;
cout << p->item << " ";
prePrint(p->lchild);
prePrint(p->rchild);
}
//中序遍历
void inPrint_o(BSTNode *p)
{
if(p == NULL)
return;
prePrint(p->lchild);
cout << p->item << " ";
prePrint(p->rchild);
}
//后序遍历
void nextPrint_o(BSTNode *p)
{
if(p == NULL)
return;
prePrint(p->lchild);
prePrint(p->rchild);
cout << p->item << " ";
}
/*--------------------------迭代遍历的几种--------------------------*/
//先序遍历
void prePrint_s(BSTNode *p)
{
if(p == NULL)
return;
stack<BSTNode *> st;
BSTNode *pr = p;
do
{
cout << pr->item <<" ";
if(pr->rchild != NULL)
{
st.push(pr->rchild);
}
pr = pr->lchild;
if(pr == NULL)
{
pr = st.top();
st.pop();
}
}while(pr != NULL);
}
//中序遍历
void inPrint_s(BSTNode *p)
{
if(p == NULL)
return;
stack<BSTNode *> st;
BSTNode *pr = p;
do
{
while(pr != NULL)
{
st.push(pr);
pr = pr->lchild;
}
if(!st.empty())
{
pr = st.top();
st.pop();
cout << pr->item << " ";
pr = pr->rchild;
}
}while(!st.empty())
}
//后序遍历
void nextPrint_s(BSTNode *p)
{
if(p == NULL)
return;
stack<BSTNode *> st;
stack<int> si; //设立一个标志位的栈
BSTNode *pr = p;
do
{
while(pr != NULL)
{
st.push(pr);
si.push(0);
pr = pr->lchild;
}
if(si.top() == 0)
{
pr = st.top()->rchild;
si.pop();
si.push(1);
}else
{
pr = st.top();
st.pop();
si.pop();
cout << pr->item << " ";
pr = NULL;
}
}while(!st.empty() && !si.empty());
}
//层次遍历
void levelPrint(BSTNode *p)
{
if(p == NULL)
return;
queue<BSTNode *> qt;
BSTNode *pr = p;
do
{
if(!qt.empty())
{
pr = qt.front();
qt.pop();
}
cout << pr->item << " ";
if(pr->lchild != NULL)
{
qt.push(pr->lchild);
}
if(pr->rchild != NULL)
{
qt.push(pr->rchild);
}
}while(!qt.empty());
}
//求二叉树叶子结点的个数
int search_leaves(BSTNode *p)
{
if(p == NULL)
return 0;
int sum = 0;
BSTNode *pr = p;
stack<BSTNode *> st;
do
{
if(pr->lchild == NULL && pr->rchild == NULL)
{
sum++;
}
if(pr->rchild != NULL)
{
st.push(pr->rchild);
}
pr = pr->lchild;
if(pr == NULL)
{
pr = st.top();
st.pop();
}
}while(pr != NULL);
return sum;
}
//求二叉树的深度
int search_depth(BSTNode *p)
{
if(p == NULL)
return 0;
queue<BSTNode *> qt;
BSTNode *pr = p;
BSTNode *re = p; //用来保存本行的最后一个结点
BSTNode *bl = NULL; //用来记录队列里元素的变化
int sum = 0;
qt.push(pr);
do
{
if(!qt.empty())
{
pr = qt.front();
qt.pop();
}
if(pr->lchild != NULL)
{
qt.push(pr->lchild);
bl = pr->lchild;
}
if(pr->rchild != NULL)
{
qt.push(pr->rchild);
bl = pr->rchild;
}
if(pr == re)
{
sum++;
re = bl;
}
}while(!qt.empty());
return sum;
}
//二叉树的查找
BSTNode *search_node(BSTNode *current, int item)
{
if(item < current->item)
{
if(current->lchild == NULL)
{
return NULL;
}
return search_node(current->lchild, item);
}else if(item > current->item)
{
if(current->rchild == NULL)
{
return NULL;
}
return search_node(current->rchild, item);
}
return current;
}
/*
二叉树结点的删除
*/
//查找要删除的结点的父节点
BSTNode *btree_find(BSTNode *p, int value, int *pos)
{
BSTNode *backfather = NULL;
BSTNode *pr = p;
backfather = p;
*pos = 0;
while(pr != NULL)
{
if(pr->item == value)
{
return backfather;
}else
{
backfather = pr;
if(pr->item > value)
{
pr = pr->lchild;
*pos = -1;
}else
{
pr = pr->rchild;
*pos = 1;
}
}
}
return NULL;
}
//二叉树结点删除
void delete_node(BSTNode *p, int value)
{
BSTNode *backfather = NULL;
BSTNode *pr = p;
BSTNode *next = NULL;
int pos;
backfather = btree_find(p, value, &pos);
if(backfather == NULL)
return ;
switch(pos)
{
case -1: pr = backfather->lchild; break;
case 1; pr = backfather->rchild; break;
case 0; pr = backfather; break;
}
if(pr->lchild == NULL || pr->rchild == NULL)
{
if(pos == 0)
{
if(pr->rchild != NULL)
{
p = p->rchild;
}else
{
p = p->lchild;
}
}else if(pos < 0)
{
if(pr->lchild == NULL)
{
backfather->lchild = pr->rchild;
}else
{
backfather->lchild = pr->lchild;
}
}else
{
if(pr->lchild == NULL)
{
backfather->rchild = pr->rchild;
}else
{
backfather->rchild = pr->lchild;
}
}
free(pr);
return;
}
/*有左子树也有右子树的情况 */
backfather = pr; //父节点指向当前节点
next = pr->lchild; //设置子节点
while (next->rchild != NULL)
{
backfather = next;
next = next->rchild;
}
pr->item = next->item; //替换数据
//把最右面的结点删除
if (backfather->lchild == next)
{
backfather->lchild = next->lchild;
}
else
{
backfather->rchild = next->lchild;
}
free(next);
return;
}
//二叉树的销毁
void destroy_btree(BSTNode *p)
{
if(p == NULL)
return;
destroy_btree(p->lchild);
destroy_btree(p->rchild);
free(p);
}
int main()
{
return 0;
}