二叉搜索树(二叉排序树或二叉查找树)(BST,Binary Search Tree):
或者是一颗空树,若不为空,则:
(1)非空左子树的所有键值小于根结点的键值;
(2)非空右子树的所有键值大于根结点的键值;
(3)左右子树分别也是二叉搜索树。
结构定义与操作集:
//二叉排序树
#include <stdio.h>
#include <stdlib.h>
#define ElementType int
typedef struct BinSerTree{
ElementType data; //下标为0的位置记录树中元素的个数
struct BinSerTree *Left, *Right;
}BTree;
typedef BTree* BST;
typedef BTree* Position;
Position Find( ElemengtType x, BST ptrt ); //查找递归算法
Position Find_( ElemengtType x, BST ptrt ); //查找非递归算法
Position FindMax( BST ptrt ); //找最大值
Position FindMin( BST ptrt ); //找最小值
BST Insert( ElementType x, BST ptrt ); //插入
BST Delete( ElementType x, BST ptrt ); //删除
void CreatBST( BST *ptrt, ElementType s[], int n ); //创建二叉搜索树
二叉排序树的查找:
(1)递归写法:
Position find( ElemengtType x, BST ptrt );
{
if( IsEmpty( ptrt ) ){
printf( "树空" );
return NULL;
}
if( ptrt -> data > x )
return find( x, ptrt -> Left );
else if( ptrt -> data < x )
return find( x, ptrt -> Right );
else
return ptrt;
}
(2)非递归写法:
Position find( ElemengtType x, BST ptrt );
{
while( ptrt != NULL ){
if( ptrt -> data > x );
ptrt = ptrt -> Left;
else if( ptrt -> data < x )
ptrt = ptrt -> Right;
else
return ptrt;
}
return NULL;
}
查找的效率取决于树的高度。
找最大值:
Position FindMax( BST ptrt )
{
if( IsEmpty( ptrt ) ){
printf( "树空" );
return NULL;
}
while( ptrt -> Right != NULL ){
ptrt = ptrt -> Right;
}
return ptrt;
}
找最小值:
Position FindMin( BST ptrt )
{
if( IsEmpty( ptrt ) ){
printf( "树空" );
return NULL;
}
while( ptrt -> Left != NULL ){
ptrt = ptrt -> Left;
}
return ptrt;
}
插入:
BST Insert( ElementType x, BST ptrt )
{
if( IsEmpty( ptrt ) ){
BST s = ( BST )malloc( sizeof( BTree ) );
s -> data = x;
s -> Left = s -> Right = NULL;
return s;
}
else
if( ptrt -> data > x )
BST Insert( x, ptrt -> Left );
else if( ptrt -> data < x )
BST Insert( x, ptrt -> Right );
return ptrt;
}
构建二叉搜索树:
void CreatBST( BST *ptrt, ElementType s[], int n )
{
ptrt = NULL;
int i = 0;
while( i < n ){
Insert( s[i], *ptrt );
i++;
}
}
删除:
BST Delete( ElementType x, BST ptrt )
{
Position tmp;
if( ptrt == NULL ){
printf( "NOT FOUND!\n" );
return NULL;
}
if( x < ptrt -> data )
ptrt -> Left = Delete( x, ptrt -> Left );
else if( x > ptrt -> data )
ptrt -> Right = Delete( x, ptrt -> Right );
else{
if( ptrt -> Left && ptrt -> Right ){
tmp = FindMin( ptrt -> Right );
ptrt -> data = tmp -> data;
ptrt -> Right = Delete( ptrt -> data, ptrt -> Right );
}
else{
tmp = ptrt;
if( ptrt -> Left == NULL )
ptrt = ptrt -> Right;
else if( ptrt -> Right == NULL )
ptrt = ptrt -> Left;
free( tmp );
}
}
return ptrt;
}
总体代码与测试:
//二叉排序树
#include <stdio.h>
#include <stdlib.h>
#define ElementType int
typedef struct BinSerTree{
ElementType data; //下标为0的位置记录树中元素的个数
struct BinSerTree *Left, *Right;
}BTree;
typedef BTree* BST;
typedef BTree* Position;
Position Find( ElementType x, BST ptrt ); //查找递归算法
Position Find_( ElementType x, BST ptrt ); //查找非递归算法
Position FindMax( BST ptrt ); //找最大值
Position FindMin( BST ptrt ); //找最小值
BST Insert( ElementType x, BST ptrt ); //插入
BST Delete( ElementType x, BST ptrt ); //删除
void CreatBST( BST &ptrt, ElementType s[], int n ); //创建二叉搜索树
void PreOrder( BST ptrt ); //先序遍历
int main()
{
BST ptrt;
ElementType a[5] = { 3, 2, 5, 1, 4 };
CreatBST( ptrt, a, 5 );
PreOrder( ptrt );
printf( "\n" );
Delete( 3, ptrt );
PreOrder( ptrt );
printf( "\n" );
return 0;
}
Position Find( ElementType x, BST ptrt )
{
if( ptrt == NULL ){
printf( "树空" );
return NULL;
}
if( ptrt -> data > x )
return Find( x, ptrt -> Left );
else if( ptrt -> data < x )
return Find( x, ptrt -> Right );
else
return ptrt;
}
Position Find_( ElementType x, BST ptrt )
{
while( ptrt != NULL ){
if( ptrt -> data > x )
ptrt = ptrt -> Left;
else if( ptrt -> data < x )
ptrt = ptrt -> Right;
else
return ptrt;
}
return NULL;
}
Position FindMax( BST ptrt )
{
if( ptrt == NULL ){
printf( "树空" );
return NULL;
}
while( ptrt -> Right != NULL ){
ptrt = ptrt -> Right;
}
return ptrt;
}
Position FindMin( BST ptrt )
{
if( ptrt == NULL ){
printf( "树空" );
return NULL;
}
while( ptrt -> Left != NULL ){
ptrt = ptrt -> Left;
}
return ptrt;
}
BST Insert( ElementType x, BST ptrt )
{
if( ptrt == NULL ){
BST s = ( BST )malloc( sizeof( BTree ) );
s -> data = x;
s -> Left = s -> Right = NULL;
return s;
}
else
if( ptrt -> data > x )
ptrt -> Left = Insert( x, ptrt -> Left );
else if( ptrt -> data < x )
ptrt -> Right = Insert( x, ptrt -> Right );
return ptrt;
}
void CreatBST( BST &ptrt, ElementType s[], int n )
{
ptrt = NULL;
int i = 0;
while( i < n ){
ptrt = Insert( s[i], ptrt );
i++;
}
}
BST Delete( ElementType x, BST ptrt )
{
Position tmp;
if( ptrt == NULL ){
printf( "NOT FOUND!\n" );
return NULL;
}
if( x < ptrt -> data )
ptrt -> Left = Delete( x, ptrt -> Left );
else if( x > ptrt -> data )
ptrt -> Right = Delete( x, ptrt -> Right );
else{
if( ptrt -> Left && ptrt -> Right ){
tmp = FindMin( ptrt -> Right );
ptrt -> data = tmp -> data;
ptrt -> Right = Delete( ptrt -> data, ptrt -> Right );
}
else{
tmp = ptrt;
if( ptrt -> Left == NULL )
ptrt = ptrt -> Right;
else if( ptrt -> Right == NULL )
ptrt = ptrt -> Left;
free( tmp );
}
}
return ptrt;
}
void PreOrder( BST ptrt )
{
if( ptrt ){
printf( "%d ", ptrt -> data );
PreOrder( ptrt -> Left );
PreOrder( ptrt -> Right );
}
}