数据结构课程设计.docx

上传人:b****5 文档编号:30243393 上传时间:2023-08-13 格式:DOCX 页数:27 大小:177.56KB
下载 相关 举报
数据结构课程设计.docx_第1页
第1页 / 共27页
数据结构课程设计.docx_第2页
第2页 / 共27页
数据结构课程设计.docx_第3页
第3页 / 共27页
数据结构课程设计.docx_第4页
第4页 / 共27页
数据结构课程设计.docx_第5页
第5页 / 共27页
点击查看更多>>
下载资源
资源描述

数据结构课程设计.docx

《数据结构课程设计.docx》由会员分享,可在线阅读,更多相关《数据结构课程设计.docx(27页珍藏版)》请在冰豆网上搜索。

数据结构课程设计.docx

数据结构课程设计

 

数据结构课程设计(通讯录制作)(总26页)

一.设计内容(通讯录)

本系统应完成一下几方面的功能:

1) 输入信息——enter();

2) 显示信息———display();

3) 查找以姓名作为关键字———search();

4) 删除信息———delete();

5) 存盘———save();

6) 装入———load();

设计要求:

1) 每条信息至包含:

姓名(NAME)街道(STREET)城市(CITY)邮编(EIP)国家(STATE)几项

2) 作为一个完整的系统,应具有友好的界面和较强的容错能力

二.设计思路

通过visualc++(用的是C语言)编写一个dos界面的控制台程序,该程序通过链表的操作,文件存储来实现通讯录的基本功能

structaddress{/*定义结构*/

charname[10];/*姓名*/

charstreet[50];/*街道*/

charcity[10];/*城市*/

charstate[15];/*国家*/

chareip[7];/*邮编*/

structaddress*next;/*后继指针*/

structaddress*prior;/*前驱指针*/

}

链表的插入,删除来实现通讯录里的内容的插入删除

当操作完成通过文件件来存储链表的信息,下次打开程序时,读取文件里的内容到内存中,放在链表,然后又可以对链表进行操作;

 

在这里面,文件内容不可以在外部更改,只能通过读取到内存链表中,通过程序进行更改,然后再写入到文件,写入过程会覆盖上次的内容。

structaddress*start;/*首结点*/

structaddress*last;/*尾结点*/

structaddress*find(char*);/*声明查找函数*/

voidenter();/*函数声明*/

voidsearch();/*查找,查找过程中调用find函数*/

voidsave();/*存盘,将链表信息保存到文件中*/

voidload();/*导入,将文件内容导入到内存链表中*/

voidlist();/*显示当前链表中信息*/

voidddelete(structaddress**,structaddress**);

voidinsert(structaddress*i,structaddress**start,

structaddress**last);

voidinputs(char*,char*,int);

voiddisplay(structaddress*);

intmenu_select(void);

三.详细设计

1.主界面设计

通过switch语句调用各种函数,实现各种操作。

然后把switch嵌套到无限的for循环(for(;;))中,使完成每一步操作都回到到选择操作的主界面

voidmain()

{

start=last=NULL;

for(;;)/*无限循环*/

{

switch(menu_select())/*调用主界面的选择函数,带回返回值*/

{

case1:

enter();

continue;

case2:

ddelete(&start,&last);

continue;

case3:

list();

continue;

case4:

search();

continue;

case5:

save();

continue;

case6:

load();

continue;

case7:

exit(0);

}

}

}

intmenu_select(void)/*主目录*/

{

chars[80];

intc;

printf("………………^欢迎使用DOS通讯录系统^………………\n");

printf("************请在做其它操作前先导入*************\n");

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

printf("*****************1.输入信息******************\n");

printf("*****************2.删除信息******************\n");

printf("*****************3.显示信息******************\n");

printf("*****************4.查找******************\n");

printf("*****************5.存盘******************\n");

printf("*****************6.导入******************\n");

printf("*****************7.退出******************\n");

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

do{

printf("\nPleaseenteryourchoice:

\n");

gets(s);

c=atoi(s);/*将获取的字符串转换成整型*/

}while(c<0||c>7);

returnc;/*返回输入值*/

}

2.输入信息函数

输入函数:

structaddress*info;/*定义当前结点*/

for(;;)

{

info=(structaddress*)malloc(sizeof(structaddress));/*为当前结点分配空间*/

if(!

info)

{

printf("\nOutofmemory");

exit(0);/*如果分配空间失败,退出程序*/

}

printf("输入空姓名结束:

\n");

inputs("请输入姓名:

",info->name,10);

if(!

info->name[0])break;/*如果输入姓名为空,结束循环*/

inputs("请输入街道:

",info->street,50);

inputs("请输入城市:

",info->city,15);

inputs("请输入国家:

",info->state,15);

inputs("请输入邮编:

",info->eip,7);

insert(info,&start,&last);/*调用结点插入函数*/

}

输入函数调用到另外两个函数,inputs和insert

其中inputs中还用到fgets(str,n,fp),把键盘的输入信息传到

字符串中

charp[255];

do

{

printf(prompt);

fgets(p,254,stdin);/*stdin,标准输入缓存,获取键盘输入信息*/

if(strlen(p)>count)

printf("\nTooLong\n");

}while(strlen(p)>count);

p[strlen(p)-1]=0;

strcpy(s,p);

insert是关键函数,每当输入完一条信息都会调用到insert函数,将信息插入到链表中

if(*last==NULL)/*如果尾结点为空,意味着当前链表为空*/

{/*则将该结点赋给头尾结点*/

i->next=NULL;

i->prior=NULL;

*last=i;

*start=i;

return;

}

else/*如果链表不为空,则将信息插入到链表尾,作为尾结点*/

{

(*last)->next=i;

i->prior=*last;

i->next=NULL;

*last=(*last)->next;

}

NULL

NULL

 

插入信息会显示在链表最后

 

3.删除·查找·显示函数

删除函数调用find函数,通过姓名,查找到该节点,然后删除该节点信息,这其中涉及到头尾节点,及其变化;

先判断是否为头结点,如果为头结点,则把原头结点的后继作为新的头结点

如果不为头结点,则该节点的前驱的next指向该节点的后继

如果该节点为尾结点,则让该节点的前驱作为新的尾结点

structaddress*info;

chars[80];

inputs("请输入姓名:

",s,10);

info=find(s);

if(info)

{

printf("Deleting......\n");

if(*start==info)

{

*start=info->next;

if(*start)

(*start)->prior=NULL;

else*last=NULL;

}

else

{

{info->prior->next=info->next;

if(info!

=*last)

info->next->prior=info->prior;

else

*last=info->prior;

}

free(info);

printf("-Ok,删除成功!

\n");

}

与删除相比,查找就简单的多,只需要调用find的函数,找到该节点记录并显示出来就行了,在search本身里面只要调整下输出的界面就行了

structaddress*find(char*name)/*查找函数,形参为欲查找结点的name域*/

{

structaddress*info;

info=start;

while(info)

{

if(!

strcmp(name,info->name))

returninfo;

info=info->next;

}

printf("Namenotfound.\n");

returnNULL;

}

输出函数更简单,直接输出链表即可

if(info==NULL)

printf("当前记录为空!

");

else

printf("姓名\t街道\t\t城市\t国家\t邮编\t\n");

while(info)

{

display(info);/*display为输出节点函数,一些列print组成*/

if(info->next==NULL)

{break;}info=info->next;

};

 

4.存储与导入

存储

存储时通过fopen打开文件(没有该文件时则创建)

fp=fopen("","wb");/*生成文件*/

if(!

fp)

{printf("Cannotopenfile.\n");return}

然后通过fwrite将链表信息写入文件

while(info)/*把链表写入文件*/

{fwrite(info,sizeof(structaddress),1,fp);

info=info->next;}

fwrite每次从info读取一个sizeof(structaddress)长度的数据,

写入fp文件中。

写入完毕后即关闭文件

fclose(fp);

导入

导入时先建立链表,为节点分配内存空间

然后打开文件,将文件的内容写入内存链表中

registerintt,size;

structaddress*info,*temp=0;

char*p;

FILE*fp;/*打开文件*/

if((fp=fopen("","r"))==NULL)

{

printf("Cannotopenfile!

\n");

return;

}

printf("\n\nLoading...\n");/*调用文件*/

size=sizeof(structaddress);/*为结点分配内存*/

start=(structaddress*)malloc(size);

if(!

start)/*如果读取失败,返回*/

{

printf("Outofmemory!

\n");

exit(0);

}

info=start;

p=(char*)info;

while((*p++=getc(fp))!

=EOF)

{

for(t=0;t

*p++=getc(fp);

info->next=(structaddress*)malloc(size);

if(!

info->next)

{

printf("Outofmemory!

\n");

return;

}

info->prior=temp;

temp=info;

info=info->next;

p=(char*)info;

}

temp->next=0;

last=temp;

start->prior=0;

fclose(fp);

注意:

每次文件存储的时候都会覆盖以前存在文件里的内容,而每次导入的时候都会改变链表的内容。

因此每次打开程序时请先导入存储在文件里的数据,或者将备份存储起来,避免数据丢失。

 

四.设计总结

通过本次课程设计,我学到了很多东西。

以前从没有用过文件方面的知识,而这次设计中用到了,刚开始使用时出了很多问题,在文件存储时经常遇到意外错误而导致程序终止了。

这次的实验使我对结构体,链表的认识更深刻,使用更熟练,刚开始时在链表插入时遇到好多次内存方面的错误,还有插入操作时对指针的使用不太熟练。

通过一次次的思考与实验,思路更加清晰,程序的容错能力也越来越强。

这次实验让我学到很多书本上没有的东西。

程序里多次用到for(;;)循环,还有(structaddress*)malloc(sizeof(structaddress))为节点分配内存空间。

在文件操作中主要涉及到的函数有:

fopen(”文件名”,”使用文件方式”);

fwrite(info,sizeof(structaddress),1,fp);

fclose(文件指针);

五.参考资料

C程序设计(第三版)谭浩强清华大学出版社

数据结构(C++版)李根强中国水利水电出版社

 

附完整源码:

#include<>

#include<>

#include<>

structaddress{/*定义结构*/

charname[10];

charstreet[50];

charcity[10];

charstate[15];

chareip[7];

structaddress*next;/*后继指针*/

structaddress*prior;/*前驱指针*/

};

structaddress*start;/*首结点*/

structaddress*last;/*尾结点*/

structaddress*find(char*);/*声明查找函数*/

voidenter();/*函数声明*/

voidsearch();

voidsave();

voidload();

voidlist();

voidddelete(structaddress**start,structaddress**last);

voidinsert(structaddress*i,structaddress**start,

structaddress**last);

voidinputs(char*,char*,int);

voiddisplay(structaddress*);

intmenu_select(void);

 

voidmain()

{

start=last=NULL;

for(;;)

{

switch(menu_select())

{

case1:

enter();

continue;

case2:

ddelete(&start,&last);

continue;

case3:

list();

continue;

case4:

search();

continue;

case5:

save();

continue;

case6:

load();

continue;

case7:

exit(0);

}

}

}

intmenu_select(void)/*主目录*/

{

chars[80];

intc;

printf("………………^欢迎使用DOS通讯录系统^………………\n");

printf("************请在做其它操作前先导入*************\n");

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

printf("*****************1.输入信息******************\n");

printf("*****************2.删除信息******************\n");

printf("*****************3.显示信息******************\n");

printf("*****************4.查找******************\n");

printf("*****************5.存盘******************\n");

printf("*****************6.导入******************\n");

printf("*****************7.退出******************\n");

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

do{

printf("\nPleaseenteryourchoice:

\n");

gets(s);

c=atoi(s);

}while(c<0||c>7);

returnc;/*返回输入值*/

}

voidenter()/*输入函数,本函数循环输入资料,当输入姓名为空时退出*/

{

structaddress*info;/*定义当前结点*/

for(;;)

{

info=(structaddress*)malloc(sizeof(structaddress));/*为当前结点分配空间*/

if(!

info)

{

printf("\nOutofmemory");

exit(0);/*如果分配空间失败,退出程序*/

}

printf("输入空姓名结束:

\n");

inputs("请输入姓名:

",info->name,10);

if(!

info->name[0])

break;/*如果输入姓名为空,结束循环*/

inputs("请输入街道:

",info->street,50);

inputs("请输入城市:

",info->city,15);

inputs("请输入国家:

",info->state,15);

inputs("请输入邮编:

",info->eip,7);

insert(info,&start,&last);/*调用结点插入函数*/

}

}

voidinputs(char*prompt,char*s,intcount)/*输入函数,有越界检测功能*/

{

charp[255];

do

{

printf(prompt);

fgets(p,254,stdin);

if(strlen(p)>count)

printf("\nTooLong\n");

}while(strlen(p)>count);

p[strlen(p)-1]=0;

strcpy(s,p);

}

voidinsert(/*数据插入函数*/

structaddress*i,

structaddress**start,

structaddress**last

{

if(*last==NULL)/*如果尾结点为空,意味着当前链表为空*/

{

i->next=NULL;

i->prior=NULL;

*last=i;

*start=i;

return;

}

else

{

(*last)->next=i;

i->prior=*last;

i->next=NULL;

*last=(*last)->next;

}

 

}

voidddelete(structaddress**start,structaddress**last)/*删除函数*/

{

structaddress*info;

chars[80];

inputs("请输入姓名:

",s,10);/*输入欲删除结点的name域内容*/

info=find(s);/*查找该内容*/

if(info)/*如果找到*/

{

printf("Deleting......\n");

if(*start==info)/*如果该结点为首结点,把该结点的下驱作为新的首结点(入口)*/

{

*start=info->next;

if(*start)

(*start)->prior=NULL;

else*last=NULL;

}

else/*如果欲删除的结点不是首结点*/

{

info->prior->next=info->next;/*令该结点的前驱的next指针指向该结点的后驱,

*又令该结点的后驱的prior指点指向该结点的前驱*/

if(info!

=*last)/*如果该结点是尾结点,则令该结点的前驱为尾结点*/

info->next->prior=info->prior;

else

*last=info->prior;

}

free(info);/*释放该结点所占用的内存*/

printf("-Ok,删除成功!

\n");

}

}

structaddress*find(char*name)/*查找函数,形参为欲查找结点的name域*/

{

structaddress*info;

info=start;

while(info)

{

if(!

s

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

当前位置:首页 > 表格模板 > 合同协议

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

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