数据结构课程设计之二叉排序树的实现.docx

上传人:b****6 文档编号:6428492 上传时间:2023-01-06 格式:DOCX 页数:17 大小:292.63KB
下载 相关 举报
数据结构课程设计之二叉排序树的实现.docx_第1页
第1页 / 共17页
数据结构课程设计之二叉排序树的实现.docx_第2页
第2页 / 共17页
数据结构课程设计之二叉排序树的实现.docx_第3页
第3页 / 共17页
数据结构课程设计之二叉排序树的实现.docx_第4页
第4页 / 共17页
数据结构课程设计之二叉排序树的实现.docx_第5页
第5页 / 共17页
点击查看更多>>
下载资源
资源描述

数据结构课程设计之二叉排序树的实现.docx

《数据结构课程设计之二叉排序树的实现.docx》由会员分享,可在线阅读,更多相关《数据结构课程设计之二叉排序树的实现.docx(17页珍藏版)》请在冰豆网上搜索。

数据结构课程设计之二叉排序树的实现.docx

数据结构课程设计之二叉排序树的实现

 

中南大学信息科学与工程学院

 

 

课题名称:

二叉排序树的实现

信息科学与工程学院

通信工程

院:

级:

号:

名:

指导老师:

漆华妹

 

完成日期——2014年7月10日

数据结构课程设计

一、引言

数据结构是一门理论性强、思维抽象、难度较大的课程,是基础课和专业课之间的桥梁。

该课程的先行课程是计算机基础、程序设计语言、离散数学等,后续课程有操作系统、编译原理、数据库原理、软件工程等。

通过本门课程的学习,我们应该能透彻地理解各种数据对象的特点,学会数据的组织方法和实现方法,并进一步培养良好的程序设计能力和解决实际问题的能力。

数据结构是计算机科学与技术专业的一门核心专业基础课程,在该专业的课程体系中起着承上启下的作用,学好数据结构对于提高理论认知水平和实践能力有着极为重要的作用。

学习数据结构的最终目的是为了获得求解问题的能力。

对于现实世界中的问题,应该能从中抽象出一个适当的数学模型,该数学模型在计算机内部用相应的数据结构来表示,然后设计一个解此数学模型的算法,再进行编程调试,最后获得问题的解答。

实习课程是为了加强编程能力的培养,鼓励学生使用新兴的编程语言。

相信通过数据结构课程实践,无论是理论知识,还是实践动手能力,我们都会有不同程度上的提高。

二、课程设计目的

本课程是数据结构课程的实践环节。

主要目的在于加强学生在课程中学习的相关算法和这些方法的具体应用,使学生进一步掌握在C++或其他语言中应用这些算法的能力。

通过课程设计题目的练习,强化学生对所学知识的掌握及对问题分析和任务定义的理解。

三、问题描述及基本要求

二叉排序树的实现:

用顺序和二叉链表作存储结构

1)以回车(‘\n’)为输入结束标志,输入数列L,生成一棵二叉排序树T;

2)对二叉排序树T作中序遍历,输出结果;

3)输入元素x,查找二叉排序树T,若存在含x的结点,则删除该结点,并作中序遍历(执行操作2);否则输出信息“无x”。

一、问题分析和任务定义

在设计之前,首先应该充分地分析和理解问题,明确问题要求做什么?

限制条件是什么?

对所需完成的任务作出明确的回答。

二、系统设计

系统设计分为逻辑设计和详细设计两步。

逻辑设计指的是,对问题描述中的操作对象定义相应的数据类型,并按照以数据结构为中心的原则划分模块,定义软件模块结构图;详细设计则为定义相应的存储结构,并写出各函数模块的伪码算法。

三、编码实现和调试

四、软件模块结构图

五、程序设计流程图(设计思想)

无结点x

存在含x的结点,则删除该结点,并作中序遍历

输入元素x,查找二叉排序树T

 

详细设计思想:

建立二叉排序树采用边查找边插入的方式。

查找函数采用递归的方式进行查找。

如果查找到相等的则插入其左子树。

然后利用插入函数将该元素插入原树。

对二叉树进行中序遍历采用递归函数的方式。

在根结点不为空的情况下,先访问左子树,再访问根结点,最后访问右子树。

删除结点函数,采用边查找边删除的方式。

如果没有查找到,进行提示;如果查找到结点则将其左子树最右边的节点的数据传给它,然后删除其左子树最右边的节点。

 

六、源代码

1、用二叉链表存储结构实现

#include

typedefintKeyType;

typedefcharElemType[10];

typedefstructtnode

{

KeyTypekey;

ElemTypedata;

structtnode*lchild,*rchild;

}BSTNode;

voidBSTdisp(BSTNode*b);

BSTNode*BSTSearch(BSTNode*bt,KeyTypek)

{

BSTNode*p=bt;

while(p!

=NULL&&p->key!

=k)

{

if(kkey)

p=p->lchild;/*沿左子树查找*/

else

p=p->rchild;/*沿右子树查找*/

}

return(p);

}

intBSTInsert(BSTNode*&bt,KeyTypek)

{

BSTNode*f,*p=bt;

while(p!

=NULL)

{

if(p->key==k)

return(0);

f=p;/*f指向*p结点的双亲结点*/

if(p->key>k)

p=p->lchild;/*在左子树中查找*/

else

p=p->rchild;/*在右子树中查找*/

}

p=newBSTNode;/*建立新结点*/

p->key=k;

p->lchild=p->rchild=NULL;

if(bt==NULL)/*原树为空时,*p作为根结点插入*/

bt=p;

elseif(kkey)

f->lchild=p;/*插入*p作为*f的左孩子*/

else

f->rchild=p;/*插入*p作为*f的右孩子*/

return

(1);

}

/*BSTNode*CreatBST(KeyTypeA[],intn)

//由数组中的关键字建立一棵二叉排序树

{

BSTNode*bt=NULL;//初始时bt为空树

inti=0;

while(i

if(BSTInsert(bt,A[i]))//将A[i]插入二叉排序树T中

{

count<<"第"<

"<

DispBST(bt);printf("\n");

i++;

}

returnbt;//返回建立的二叉排序树的根指针

}*/

voidCreateBST(BSTNode*&bt,KeyTypestr[],intn)

{

bt=NULL;/*初始时bt为空树*/

inti=0;

while(i

{

BSTInsert(bt,str[i]);/*将关键字str[i]插入二叉排序树bt中*/

i++;

}

}

intBSTDelete(BSTNode*&bt,KeyTypek)

{

BSTNode*p=bt,*f,*r,*f1;

f=NULL;/*p指向待比较的结点,f指向*p的双亲结点*/

while(p!

=NULL&&p->key!

=k)/*查找值域为x的结点*/

{f=p;

if(p->key>k)

p=p->lchild;/*在左子树中查找*/

else

p=p->rchild;/*在右子树中查找*/

}

if(p==NULL)/*未找到key域为k的结点*/

return(0);

elseif(p->lchild==NULL)/**p为被删结点,若它无左子树*/

{

if(f==NULL)/**p是根结点,则用右孩子替换它*/

bt=p->rchild;

elseif(f->lchild==p)/**p是双亲结点的左孩子,则用其右子替换它*/

{f->lchild=p->rchild;

deletep;

}

elseif(f->rchild==p)/**p是双亲结点的右孩子,则用其右孩子替换它*/

{f->rchild=p->rchild;

deletep;

}

}

elseif(p->rchild==NULL)/**p为被删结点,若它无右子树*/

{

if(f==NULL)/**p是根结点,则用左孩子替换它*/

bt=p->lchild;

if(f->lchild==p)/**p是双亲结点的左孩子,则用其左孩子替换它*/

{f->lchild=p->lchild;

deletep;

}

elseif(f->rchild==p)/**p是双亲结点的右孩子,则用其左孩子替换它*/

{f->rchild=p->lchild;

deletep;

}

}

else/**p为被删结点,若它有左子树和右子树*/

{

f1=p;r=p->lchild;/*查找*p的左子树中的最右下结点*r*/

while(r->rchild!

=NULL)/**r一定是无右子树的结点,*f1作为r的双亲*/

{f1=r;

r=r->rchild;

}

if(f1->lchild==r)/**r是*f1的左孩子,删除*r*/

f1->lchild=r->rchild;

elseif(f1->rchild==r)/**r是*f1的右孩子,删除*r*/

f1->rchild=r->lchild;

r->lchild=p->lchild;/*以下语句是用*r替代*p*/

r->rchild=p->rchild;

if(f==NULL)/**f为根结点*/

bt=r;/*被删结点是根结点*/

elseif(f->lchild==p)/**p是*f的左孩子*/

f->lchild=r;

else/**p是*f的右孩子*/

f->rchild=r;

deletep;

}

return

(1);

}

//先序遍历

/*voidpreorder(BSTNode*t)

{

if(t!

=0)

{

cout<key<<"";

preorder(t->lchild);

preorder(t->rchild);

}

}*/

//中序遍历

voidinorder(BSTNode*t)

{

if(t!

=0)

{

inorder(t->lchild);

cout<key<<"";

inorder(t->rchild);

}

}

voidBSTdisp(BSTNode*bt)

{

if(bt!

=NULL)

{

cout<key;

if(bt->lchild!

=NULL||bt->rchild!

=NULL)

{

cout<<"(";

BSTdisp(bt->lchild);

if(bt->rchild!

=NULL)

cout<<",";

BSTdisp(bt->rchild);

cout<<")";

}

}

}

voidmain()

{

intn;

BSTNode*bt=NULL,*p;

KeyTypea[200],k;

cout<<"请输入元素个数n:

";

cin>>n;

cout<<"请输入数据:

";

for(inti=0;i

{

cin>>a[i];

}

CreateBST(bt,a,n);

cout<<"BST:

";

BSTdisp(bt);cout<

cout<<"中序遍历二叉排序树:

"<

inorder(bt);

cout<<"\n";

//cout<<"先序遍历二叉排序树:

";

//preorder(bt);

//cout<<"\n";

cout<<"输入要查找的元素x:

";

cin>>k;

p=BSTSearch(bt,k);

if(p!

=NULL)

{

BSTDelete(bt,k);

cout<<"已经删除值为"<

cout<<"删除X后的BST:

";

BSTdisp(bt);cout<

cout<<"中序遍历二叉排序树:

";

inorder(bt);

cout<

}

else

cout<<"无"<

}

2、用顺序存储结构实现

#include

#include

#defineN100/*可建树结点的最大数目*/

typedefstruct

{

int*data;/*数组首址指针*/

intlenth;/*数组长度*/

}BST;

voidinsert(BSTT,inti,intkey)/*插入函数*/

{

if(i<1||i>N)printf("overflow!

");/*查找不成功*/

if(T.data[i]==0)T.data[i]=key;/*查找成功*/

elseif(key

elseif(key>T.data[i])insert(T,2*i+1,key);/*在右子树中继续查找*/

}

BSTcreate(int*crew,intnum)/*创建二插排序树的函数*/

{

BSTT;

inti,j;

T.data=(int*)malloc(N*sizeof(int));/*数组初始化*/

for(j=0;j

T.lenth=0;

for(i=0;i

{

insert(T,1,crew[i]);

++T.lenth;/*记录树中结点的个数*/

}

return(T);

}

intsearch(BSTT,intkey,inti)/*查找函数*/

{

if(!

T.data[i])return(0);/*查找不成功*/

elseif(key==T.data[i])return(i);/*查找成功*/

elseif(key

elsesearch(T,key,2*i+1);/*在右子树中继续查找*/

}

BSTcancle(BSTT,intkey)/*删除函数*/

{

BSTQ;

inti;

Q.data=(int*)malloc(N*sizeof(int));/*重新初始化一个数组Q*/

for(i=0;i

Q.lenth=0;

for(i=1;i0;i++)/*T中不为要删结点的元素全部复制到Q*/

{

if(T.data[i]==0||T.data[i]==key)continue;

insert(Q,1,T.data[i]);

--T.lenth;

++Q.lenth;

}

return(Q);

}

intinordertraverse(BSTT,inti)/*中序遍历*/

{

if(T.data[i])

{

inordertraverse(T,2*i);/*中序遍历根的左子树*/

printf("%d",T.data[i]);/*输出根结点*/

inordertraverse(T,2*i+1);/*中序遍历根的右子树*/

}

}

voidmain()

{

BSTT;

intcrew[N];

inti=0;

intnum,ch=0,j;

printf("请输入一系列的数字并以0为结束符:

");

do

{

scanf("%d",&num);

if(!

num)printf("您已完成输入!

\n");

else{crew[i]=num;i++;}

}while(num);

T=create(crew,i);

printf("\n\n**********************\n");/*主程序菜单*/

printf("\n0:

退出程序!

");

printf("\n1:

中序遍历树!

");

printf("\n2:

删除树中的元素!

");

printf("\n***********************\n");

while(ch==ch)

{

printf("\nchoosetheopperationtocontinue:

");

scanf("%d",&ch);

switch(ch){

case0:

exit(0);/*0--退出*/

case1:

printf("中序遍历的结果是:

\n");

inordertraverse(T,1);/*1--中序遍历*/

break;

case2:

printf("请输入您想删除的元素:

");

scanf("%d",&num);/*3--删除某个结点*/

j=search(T,num,1);

if(j)

{

T=cancle(T,num);

printf("您已成功删除该元素!

\n");

inordertraverse(T,1);

i--;

}

elseprintf("nonode%dyouwanttodelete!

",num);

break;

default:

printf("您的输入有误,请查证后再输!

\n");

break;/*输入无效字符*/

}

}

}

 

七、测试分析及测试数据

程序运行:

1、用二叉链表存储结构实现:

 

 

2、用顺序存储结构实现:

 

 

八、总结与体会

通过为期二周的课程设计,我对计算机的应用,数据结构的作用以及C++的使用都有了更加深刻深的认识和了解。

在理论学习和上机实践的各个环节中,通过自主学习和请教老师、同学,确实获益良多。

当然在这一过程中也遭遇到了不少的问题,但也正是因为这些问题引发的思考给我带了很多很多的收获。

从当初不喜欢上机写程序到现在能主动写程序,从当初拿着程序不知如何下手到现在知道如何分析问题,如何用专业知识解决实际问题的转变,我发现无论是专业知识还是动手能力,自己都有很大程度的提高。

通过课程设计题目的练习,强化学生对所学知识的掌握及对问题分析和任务定义的理解。

在这段时间里,我遇到过的问题主要就是C语言和C++语言有些混淆,一些用法记不太清楚。

在老师的指导帮助下,同学们课余时间的讨论中,这些问题都一一得到了解决。

在程序的调试能力上,无形中得到了许多的提高。

例如:

头文件的使用,变量和数组的范围问题,定义变量时出现的问题等等。

在实际的上机操作过程中,我进一步的了解并掌握了二叉链表的建立方法和二叉排序树的构造方法,对函数的构造以及调用也有了更进一步的掌握,这让我在调试程序方面也是有了一定的经验。

当然这一切不仅仅是让我们了解数据结构的理论知识,更重要的是培养解决实际问题的能力,所以相信通过此次实习可以提高我们分析设计能力和编程能力,为后续课程的学习及实践打下良好的基础。

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 外语学习 > 英语学习

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1