数据结构课程实验报告9Word文件下载.docx
《数据结构课程实验报告9Word文件下载.docx》由会员分享,可在线阅读,更多相关《数据结构课程实验报告9Word文件下载.docx(47页珍藏版)》请在冰豆网上搜索。
![数据结构课程实验报告9Word文件下载.docx](https://file1.bdocx.com/fileroot1/2022-12/31/8a571392-0833-41c2-9e2a-326bbfe0bbe1/8a571392-0833-41c2-9e2a-326bbfe0bbe11.gif)
typedefintElemType;
IntiaList:
构造空的线性表7.LocateElem:
定位值元素位置
2.DestroyList:
销毁线性表8.PriorElem:
获取元素前驱
3.ClearList:
清空线性表9.NextElem:
获取元素后继
4.ListEmpty:
判断线性表为空10.ListInsert:
插入元素
5.ListLength:
判断表长11.ListDelete:
删除元素
6.GetElem:
获取第i个元素的值12.ListTrabverse:
遍历元素
0.Exit:
退出功能选择13.SaveFile:
保存文件
功能的具体设计
1.IntiaList构造空的线性表
源代码及注释:
statusIntiaList(SqList&
L){
=(ElemType*)malloc(LIST_INIT_SIZE*sizeof(ElemType));
GetElem获取第i个元素的值
源代码及注释:
statusGetElem(SqListL,inti,ElemType&
e){
if(!
{printf("
线性表不存在,错误\n\n"
);
returnERROR;
}
elseif==0){printf("
该表为空表,错误\n\n"
returnERROR_2;
if(i<
0||i>
位置错误,线性表位序i区间为[0,%d]\n\n"
;
returnERROR_3;
e=[i];
printf("
线性表中第%d个位置元素为%d\n\n"
i,[i]);
returnOK;
7.LocateElem:
statusLocateElem(SqListL,ElemTypee){
inti;
for(i=0;
i<
=&
&
e!
=[i];
i++){;
if(i=={printf("
线性表中没有%d这个元素\n\n"
e);
returnERROR_2;
线性表中有%d这个元素,在第%d个位置\n\n"
e,i);
returni;
8.PriorElem获取元素前驱
源代码及注释:
statusPriorElem(SqListL,ElemTypecur_e,ElemType&
pre_e){
线性表不存在,错误\n"
该表为空表,错误\n"
cur_e!
线性表中没有%d这个元素\n"
cur_e);
elseif(i==0){printf("
线性表中有%d这个元素,但为最前一个元素,无前驱\n"
returnERROR_3;
pre_e=[i-1];
returnOK;
9.NextElem获取元素后继
statusNextElem(SqListL,ElemTypecur_e,ElemType&
next_e){
elseif(i=={printf("
线性表中有%d这个元素,但为最后一个元素,无后驱\n"
next_e=[i+1];
代码说明:
由于“PriorElem获取元素前驱”和“NextElem:
获取元素后继”在实现上基本一致,算法同上,不再赘述,故此流程图省略。
10.ListInsert插入元素
statusListInsert(SqList&
inti,j,flog=0;
ElemTypee;
线性表不存在!
\n"
if==0){
由于该表为空表,请输入要插入的元素值,该元素将放在第0个位置\n\n"
scanf("
%d"
&
e);
[0]=e;
++;
是否继续插入,输入“1”确定,输入“0”退出\n\n"
flog);
while(flog){
请输入要插入的元素e和插入的位序i,位序i应满足区间[0,%d]\n\n"
scanf("
%d%d"
e,&
i);
插入位置错误,位序i应满足区间[0,%d]\n\n"
for(j=;
j>
=i;
j--)[j+1]=[j];
[i]=e;
++;
已将元素%d插入第%d个位置\n\n"
}
代码说明:
考虑到插入函数使用频繁,为方便操作,特地使用while语句循环插入元素,设置flog标志,当输入1则继续插入,输入0终止插入。
另外函数做了许多异常处理的判断:
线性表不存在则报错;
线性表为空时则直接把元素插到第0个位置,其他情况系统会提示合理的插入区间,按照区间插入即可,否则插入不成功,报错。
流程图:
11.ListDelete删除元素
statusListDelete(SqList&
L,inti,ElemType&
e){
intj;
删除位置错误,位序i应满足区间[0,%d]\n\n"
for(j=i;
j<
=;
j++)[j]=[j+1];
;
删除元素%d成功\n"
代码说明:
考虑到用户删除元素时可以方便知道线性表有多少元素可以删除,故在删除操作前提示用户。
12.ListTrabverse:
statusListTrabverse(SqListL){
Inti;
\n-------------------allelements-------------------------\n"
)
;
i++)printf("
%d"
[i]);
\n-------------------------end---------------------------\n"
return;
系统实现
1.主菜单选择界面:
操作说明:
此线性表的第一个元素被定义为第0个位置。
同时对于使用频率高的功能均已使用while循环调用,功能完成后输入1则继续循环调用该功能,输入0则退出功能。
异常处理:
退出功能时要按两次Enter键,如果在第一次按Enter键前输入了一个两位数,系统会按两次Enter键读取,如输入10,第一次读取1,第二次读取0,而第二次读取会被当成功能选择,输入0便退出系统,防止使用出错,特此说明。
2.构造空的线性表
直接输入“1”即可创建空线性表。
该函数随时可以调用,又由于此系统只设定线性表的存储空间,所以如果在对已存在的线性表进行创建空线性表时,等同于将原来的线性表置空。
3.清空线性表
图.1
图.2
在线性表存在的情况下,直接输入“1”即可创建空线性表,如图.1所示,销毁成功。
如果线性表不存在,函数会通过判断==NULL来处理异常情况,如图.2所示,销毁失败。
4.清空线性表
在线性表存在的情况下,直接输入“3”即可创建空线性表,如图.1所示,清空成功。
在这里,清空代表把[]数组的所有元素置0,同时线性表长length置0,关键就是表长为0,这是判断是否为空的依据。
在线性表不存在的情况下,函数会通过判断==NULL来处理异常情况,如图.2所示,清空失败。
5.判断线性表为空
图一
图二
图三
在线性表存在的情况下,直接输入“4”即通过判断==0是否为空线性表,如图一、图二所示。
在线性表不存在的情况下,函数会通过判断==NULL来处理异常情况,如图三显示错误。
6.判断表长
在线性表存在的情况下,直接输入“5”即通过输出判断表长。
同上面几个函数一样,排除线性表不存在情况即可。
7.获取指定位置元素
图二
在线性表存在的情况下,直接输入“6”即进入功能,输入位序后,如果存在则查找出并显示,如果不存在则显示不存在,输入0退出功能循环使用。
如图一、二。
8.定位元素位置
在线性表存在的情况下,直接输入“7”即进入功能,输入元素后,如果存在则查找出并显示位序,如果不存在则显示不存在,输入0退出功能循环使用。
如图一。
在线性表不存在的情况下,函数会通过判断==NULL来处理异常情况,如图二显示错误。
9.获取元素前驱
在线性表存在的情况下,直接输入“8”即进入功能,输入元素后,如果存在则查找出并显示前驱,如果不存在前驱则显示不存在,输入0退出功能循环使用。
在这里线性表的元素依次序有4、5、6、、、、,如果查找4的前驱,由于是第一个元素,则显示不存在前驱,如果表中没有输入的元素则会提示输入的元素不在表中。
10.获取元素后继
在线性表存在的情况下,直接输入“9”即进入功能,输入元素后,如果存在则查找出并显示前驱,如果不存在前驱则显示不存在,输入0退出功能循环使用。
在这里线性表的元素依次序有4、5、6、、、、,如果查找6的后驱,由于是最后一个元素,则显示不存在后驱,如果表中没有输入的元素则会提示输入的元素不在表中。
11.插入元素
在线性表存在的情况下,直接输入“10”即进入功能,当插入空表时,只能够把元素插入第0个位置,之后会显示插入位置的合理区间,在合理范围内则插入正确,否则失败,输入0退出功能循环使用。
在这里线性表的插入的元素依次序有4、5、6、、、、。
12.删除元素
在线性表存在的情况下,直接输入“11”即进入功能,在选择删除哪个元素时,系统会显示删除位置的合理区间,在合理范围内则删除正确,否则失败,输入0退出功能循环使用。
但是在判断是否存在线性表前,系统还是会给出一个默认的“删除合理区间”,这是系统没有优化好的地方。
13.ListTrabverse:
遍历线性表
在线性表存在的情况下,直接输入“11”即进入功能,若==NULL则如图二,若==0则如图三。
14.DataSave:
文件保存
在线性表存在的情况下,直接输入“13”即进入功能。
效率分析
声明:
系统的函数太多,故挑选重要的函数分析效率
1.GetElem获取第i个元素的值
成功时时间复杂度:
最好情况下是O
(1),最差情况下是O(n),假设在每一个元素概率都相等的情况下,平均是O(n)
失败时时间复杂度:
O(n)
2.NextElem获取元素后继
最好情况下是O
(1),最差情况下是O(n),假设在每一个元素概率都相等的情况下,平均是O(n)
3.ListInsert:
由于每次都要调整移动元素,设每个元素被插入可能性一样
最好情况下是O
(1),最差情况下是O(n),平均情况下是O(n)。
3实验二基于链式结构的线性表实现
基于链式存储结构,实现线性表的基本的,常见的运算:
要求:
typedefintStatus;
typedefintElemType;
1.IntiaList:
构造空的线性表
StatusInitList(LinkList&
L){
LinkList*l;
l=(LinkList*)malloc(sizeof(LinkList));
DestroyList:
销毁线性表
StatusDestroyList(LinkList&
if(flog==FALSE)
错误,这里没有链表要销毁\n"
else{
=0;
free;
ClearList:
清空线性表
StatusClearList(LinkList&
错误,这里没有链表要清空\n"
linkp,q;
if==0)
空链表,无须清空\n"
p=>
next;
for(i=1;
i++){ListEmpty:
判断线性表为空
StatusListEmpty(LinkListL){
错误,这里没有链表\n"
链表为空\n"
elseif!
=0)
链表非空\n"
通过判断==0来判断是否链表为空。
5.ListLength:
判断表长
intListLength(LinkListL){
else
链表长度为%d\n"
return;
通过的值得知链表长度。
6.GetElem:
获取第i个元素的值
StatusGetElem(LinkListL,inti,ElemType&
linkp;
if(flog==FALSE){printf("
线性链表不存在!
位置错误,位序i应满足区间[0,%d]\n\n"
p=;
for(j=0;
=i-1;
j++){LocateElem:
sStatusLocateElem(LinkListL,ElemTypee){
elseif==0){printf("
链表为空,无元素\n"
p->
data!
=e;
i++){PriorElem:
positionPriorpos(LinkListL,ElemTypee){
returnNULL;
inti,j;
i=LocateElem(L,e);
if(i==0){printf("
链表中元素%d无前驱元素\n"
elseif(i==1){printf("
链表中元素%d的前驱元素是%d\n"
e,>
data);
elseif(i>
1){for(j=0;
=i-2;
j++)p=p->
printf("
e,p->
returnp;
由于每个结点只有一个指针域指向下一个结点,所以只能调用LocateElem(L,e)函数顺序查找到该结点,然后根据节点位置,循环从头结点遍历到上指向一个节点的指针,并返回该指针。
9.NextElem:
positionNextElem(LinkListL,linkp){
if(i=={printf("
链表中元素%d无后驱元素\n"
=0&
{for(j=0;
由于“NextElem:
获取元素后继”与“PriorElem获取元素前驱”在实现上基本一致,算法同上,不再赘述,故此流程图省略。
10.ListInsert:
StatusListInsert(LinkList&
inti,j,tag=0;
if(flog==FALSE){printf("
错误,线性链表不存在\n"
>
data=e;
tag);
while(tag){
插入位置错误