要求:
1、用链式存储实现字典结构。
2、对构造好的二叉排序树进行中根序遍历
3、对构造好的二叉排序树进行数据的和检索
#include<stdio.h>
#include<stdlib.h>
typedef int DataType;
struct BinSearchTree //二叉排序树结点定义
{
DataType data; //数据域
struct BinSearchTree*rchild; //右子树指针
struct BinSearchTree*lchild; //左子树指针
};
typedef struct BinSearchTree *BSTree; //二叉排序树指针
//函数功能:建立二叉排序树
//输入参数:无
//返回值:二叉树的根
BSTree Creat()
{
BSTree b; //定义二叉树
DataType x;
scanf("%d", &x); //输入结点
if (x == -1)
b = NULL;
else
{
b = (BSTree)malloc(sizeof(struct BinSearchTree)); //申请空间
b->data = x; //数据域赋值
b->lchild = Creat(); //创建左结点
b->rchild = Creat(); //创建右结点
}
return b; //返回结点
}
//函数功能:检索二叉排序树
//输入参数:排序树的根,需要检索的元素
//返回值:成功返回零若不成功,返回其父结点的位置信息
BSTree SearchFindMin(BSTree T)
{
if(T == NULL)
return NULL;
if(T->lchild == NULL)
return T;
else return SearchFindMin(T->lchild);
}
//函数功能:在二叉排序树中插入某结点
//输入参数:排序树的根,需要插入的元素
//返回值:成功返回1,不成功返回0
BSTree SearchFind(BSTree T,DataType key) //左子树最大值
{
if(T == NULL)
return NULL;
if(T->data == key)
{
printf("查找成功!\n");
return T;
}
else if(T->data > key)
return SearchFind(T->lchild,key);
else
return SearchFind(T->rchild,key);
}
BSTree SearchFindMax(BSTree T) //右子树最小值
{
if(T == NULL)
return NULL;
if(T->rchild == NULL)
return T;
else return SearchFindMax(T->rchild);
}
//在给定的BST中插入结点,其数据域为element
void Insert(BSTree T,int x)
{
//这里创建一个要插入的节点
BSTree pInsert = (BSTree)malloc(sizeof(struct BinSearchTree));
pInsert->data = x;
pInsert->lchild = NULL;
pInsert->rchild = NULL;
if (T == NULL)
T = pInsert;
if (T->lchild == NULL && x < T->data)
T->lchild = pInsert;
if (T->rchild == NULL && x > T->data)
T->rchild = pInsert;
//递归实现
if (x < T->data)
Insert(T->lchild, x);
if (x > T->data)
Insert(T->rchild, x);
return;
}
//函数功能:删除二叉排序树中某个元素
//输入参数:二叉排序树的根,要删除的元素key
//返回值:无
void DeleTree(BSTree T,DataType key)
{
BSTree p, q;
p = T;
DataType temp;
while( p != NULL && key != p->data )
{
q = p;
if( key < p->data )
p = p->lchild ;
else
p = p->rchild ;
}
if( NULL == p )
printf("无此元素!\n");
else
{
//情况1:结点p的双亲结点为q,且p为叶子结点,则直接将其删除。
if( NULL == p->lchild && NULL == p->rchild )
{
if( p == q->lchild )
q->lchild = NULL;
if( p == q->rchild )
q->rchild = NULL;
free(p);
p = NULL;
}
//情况2:结点p的双亲结点为q,且p只有左子树或只有右子树,则可将p的左子树或右子树直接改为其双亲结点q的左子树或右子树。
else if( (NULL == p->rchild && NULL != p->lchild) )
{ //p只有左子树
if( p == q->lchild )
q->lchild = p->lchild ;
else if( p == q->rchild )
q->rchild = p->lchild ;
free(p);
p = NULL;
}
else if( NULL == p->lchild && NULL != p->rchild )
{ //p只有右子树
if( p == q->lchild )
q->lchild = p->rchild ;
if( p == q->rchild )
q->rchild = p->rchild ;
free(p);
p = NULL;
}
//情况3:结点p的双亲结点为q,且p既有左子树又有右子树。本代码使用直接前驱(也可以直接后继)
else
{
BSTree s, sParent;
sParent = p;
s = sParent->lchild ;
while( NULL != s->rchild )
{ //找到p的直接前驱
sParent = s;
s = s->rchild ;
}
temp = s->data ;
DeleTree( T, temp );
p->data = temp;
}
}
}
void Iorder(BSTree T)
{
if(T == NULL) //如果为空树则返回
return;
Iorder(T->lchild);
printf("%d ",T->data);//访问结点
Iorder(T->rchild);
}
void BSTdestory(BSTree T) //销毁二叉树
{
if(T != NULL)
{
BSTdestory(T->lchild);
BSTdestory(T->rchild);
free(T);
}
}
void main()
{
BSTree b;
BSTree p;
DataType x;
printf("请输入(整型)二叉排序树的先序序列:\n");
b = Creat();
printf("\n二叉排序树的中序遍历为:\n");
Iorder(b);
printf("\n");
printf("\n请输入要查找的元素(成功返回该关键词并返回其指针,不成功则返回0):");
scanf("%d",&x);
printf("%d\n",SearchFind(b,x)) ;
printf("\n请输入要插入的元素:");
scanf("%d",&x);
Insert(b,x);
printf("插入成功后的中序遍历为:\n");
Iorder(b);
printf("\n");
printf("\n请输入要删除的元素:");
scanf("%d",&x);
DeleTree(b,x);
printf("删除成功后的中序遍历:\n");
Iorder(b);
printf("\n");
BSTdestory(b);
}
本人还比较菜,代码我就懒得分头文件了,,,感兴趣的读者自己弄一下。。。
欢迎互相学习互相交流!
以下是代码运行结果的截图