资源描述
成 绩 评 定 表
学生姓名
马舒阳
班级学号
专 业
电子信息科学与技术
课程设计题目
编程技术基本实训
评
语
组长签字:
成绩
日期
年 月 日
课程设计任务书
学 院
信息科学与工程学院
专 业
电子信息科学与技术
学生姓名
马舒阳
班级学号
课程设计题目
编程技术基本实训
实践教学规定与任务:
运用C语言编写下题代码。
题目名称:设计求两数之差绝对值函数和学生成绩记录程序
内容及规定:
(1)题目一内容和规定:
1).设计一种选取式菜单。
栈子系统
******************************************************
* 1 ……入栈 *
* 2 ……出栈 *
* 3 ……显示 *
* 4 ……数制转换 *
* 0 ……返回 *
******************************************************
请选取菜单号(0…4):
2).设计一种整型数据元素链栈。
3).编写入栈、出栈和显示栈中所有元素程序。
4).编写一种把十进制数转换成八进制数应用程序。
(2)题目二内容和规定:
通讯录实质上是一种线性表,由于通讯录长度不拟定,且插入或删除操作比较频繁,因而,采用单链式存储构造。规定实现如下功能:
1).设计一种选取式菜单。
通讯录管理系统
******************************************************
* 1 ……通讯录单链表建立 *
* 2 ……通讯者插入 *
* 3 ……通讯者删除 *
* 4 ……通讯者查询 *
* 0 ……退出 *
******************************************************
请选取菜单号(0…4):
2).编程实现通讯录单链表建立、通讯者插入、通讯者删除、通讯者查询、通讯录输出。
工作筹划与进度安排:
第1天:1、指引教师布置课程设计题目及任务
2、查找有关资料
第2~4天:1、依照详细设计题目进行详细分析
2、对设计题目进行编码和调试
3、指引教师进行验收
第5天:1、指引教师针对课程设计进行答辩
2、完毕课程设计报告
指引教师:
月 日
专业负责人:
月 日
学院教学副院长:
年 月 日
目 录
一、课程设计目------------------------------------------------------------1
二、课程设计内容和规定---------------------------------------------------1
三、题目一设计过程---------------------------------------------------------2
四、题目二设计过程--------------------------------------------------------24
五、设计总结-----------------------------------------------------------------36
六、参照文献-----------------------------------------------------------------36
题目 栈子系统、通讯录管理系统
一、课程设计目
本学期咱们对《数据构造》这门课程进行了学习。这门课程是一门实践性非常强课程,为了让人们更好地理解与运用所学知识,提高动手能力,咱们进行了本次课程设计实习。这次课程设计不但规定学生掌握《数据构造》中各方面知识,还规定学生具备一定C语言基本和编程能力。
(1)题目一目:
1.掌握栈特点及其描述办法
2.掌握链式存储构造实现一种栈
3.掌握链栈各种基本操作
4.掌握栈典型应用算法
(2)题目二目:
1.掌握线性表特点
2.掌握线性表顺序存储构造和链式存储构造基本运算
3.掌握线性表基本操作
二、课程设计内容和规定
(1)题目一内容和规定:
1).设计一种选取式菜单。
栈子系统
******************************************************
* 1 ……入栈 *
* 2 ……出栈 *
* 3 ……显示 *
* 4 ……数制转换 *
* 0 ……返回 *
******************************************************
请选取菜单号(0…4):
2).设计一种整型数据元素链栈。
3).编写入栈、出栈和显示栈中所有元素程序。
4).编写一种把十进制数转换成八进制数应用程序。
(2)题目二内容和规定:
通讯录实质上是一种线性表,由于通讯录长度不拟定,且插入或删除操作比较频繁,因而,采用单链式存储构造。规定实现如下功能:
1).设计一种选取式菜单。
通讯录管理系统
******************************************************
* 1 ……通讯录单链表建立 *
* 2 ……通讯者插入 *
* 3 ……通讯者删除 *
* 4 ……通讯者查询 *
* 0 ……退出 *
******************************************************
请选取菜单号(0…4):
2).编程实现通讯录单链表建立、通讯者插入、通讯者删除、通讯者查询、通讯录输出。
三、题目一设计过程
1、题目分析
本题规定合理地设计一种栈构造及入栈、出栈、删除、查找等基本操作,并运用此构造实现数制转换。
2、 算法描述
一方面定义一种结点构造体,指针域涉及两个指针,分别指向前驱结点和后继结点,数据域为一种DataType类型变量,其中DataTYpe类型为宏定义;在定义一种栈构造体,构造体内涉及两个指针,分别为栈顶指针和栈低指针,尚有一种int型记录栈长度。
欢迎界面后,进入主菜单,主菜单用switch设计,其中调用函数NUM,该函数可返回有效菜单号,可屏蔽并提示错误信息及重新输入,菜单下调用了其她功能函数,菜单内除退出和初始化函数外所有功能函数均存储在FUN.c.下。
下面仅详细阐述一下各功能模块工作原理。
入栈为栈初次赋值,运用do{}while();可按需求循环输入多组信息,并及时退出返回到主菜单,在实现循环多组输入时调用了函数Push,Push为机械入栈一种新元素,将参数nn,入栈到栈tt内,栈长度加一。
出栈函数Pop中,一方面判断栈与否为空,为空时,不可出栈;非空时,输出栈顶元素及栈长度,并删除栈顶节点,栈长度减一。信息输出完毕后按任意键返回主菜单。
显示函数Show中,即运用do...while循环多次调用出栈函数,每次输出时要按任意键继续一次,以保障画面整洁。信息输出完毕后按任意键返回主菜单。
数制转换函数chang中,大体构造涉及一种大do...while容许多次使用信息转换,do中一方面输入数及其进制和预期进制,然后判断与否为十进制,经费是禁止数字转换为十进制,再将其循环除以预期进制,将别的数存在新建号栈中,直到余数为零,停止循环,然后依次出栈,将栈顶元素依次显示出来,即转换结束。可选N或Y,继续下一次转换,或者返回主菜单。
3、 源代码
ST.h :
#ifndef ST_H
#define ST_H
#include<stdio.h>
#include<stdlib.h>
#include<conio.h>
#include<windows.h>
typedef int DataType;
typedef struct Node
{
struct Node *pro;
DataType data;
struct Node *next;
} NN;//双向链栈结点
typedef struct
{
NN *top;
NN *base;
int size;
} ST;//栈
//main.c:主函数
//Menu.c:框架界面函数和初始化退出函数
void Initiate(ST *tt);//栈初始化 及 双向链初始化
void JM();//界面
int Num();//菜单序号选取
void Exit();//退出
//FUN.c:详细功能函数
void Input(ST *tt);//入栈
void Push(ST *tt,DataType nn);//机械入栈
int Pop(ST *tt);//机械出栈
void Show(ST tt);//显示
void change(ST tt);//数制转换
#endif
Menu.c:
#include"ST.H"
void JM()//界面函数
{
int ch;
ST tt;
Initiate(&tt);
printf("\n\n\n\n\n\n\n\n\t\t欢迎您使用 《栈子系统》 !\n\n\n ");
printf("\t\t\t\t设计者:马舒阳()\n");
getch();
do
{
system("cls");
printf ("\n\n\t\t\t\t栈子系统\n");
printf ("\t********************************************\n");
printf ("\t* 1 ……入栈 *\n");
printf ("\t* 2 ……出栈 *\n");
printf ("\t* 3 ……显示 *\n"); printf ("\t* 4 ……数制转换 *\n");
printf ("\t* 0 ……返回 *\n");
printf ("\t********************************************\n");
printf ("\t* 提示:本系统仅可用于整型数数据储存,望谅解。*\t\n");
printf ("\t********************************************\n");
ch=Num();
switch(ch)
{
case 1 :
Input(&tt);
break;
case 2 :
Pop(&tt);
break;
case 3 :
Show(tt);
break;
case 4 :
change(tt);
break;
case 0 :
Exit();
case -1:
;
}
}while(ch);
}
int Num()//判断菜单号
{
int k;
printf("\n\t\t请选取菜单号(0…4):");
scanf("%d",&k);
getchar();
if(k<0||k>5)
{
printf("\n\t\t输入错误!按任意键继续...");
getch();
return (-1);
}
else
return k;
}
void Initiate(ST *tt)
//栈空初始化 注意:此函数内tt为栈型指针,不同于JM内tt
{
tt->base = (NN*)malloc(sizeof (NN));
tt->top = tt->base;
tt->size=0;
}
void Exit()//退出
{
system("cls");
printf("\n\n\n\n\n\n\t\t谢谢使用 程序退出!");
printf("\n\n\n\n\n\n\t\t\t");
printf("按任意键继续...");
getch();
}
main.c:
#include"ST.H"
int main()
{
JM();
return 0;
}
FUN.c:
#include"ST.H"
void Input(ST *tt)//栈初始化
{
DataType nn;
int ch;
system("cls");
printf("\n\n\t\t教师早安!开始入栈!\n\n");
do
{
printf("\n\t\t请输入新栈顶数据 : ");
scanf ("%d",&nn);//%d
getchar();
Push(tt,nn);//调用入栈函数
do
{
printf("\n\t\t继续?<Y or N> ");
ch = getchar();
getchar();
if(ch != 'N' && ch != 'Y')
printf("\n\t\t请输入 Y 或 N !\n");
else
break;
}while(1);
}while (ch == 'Y');
}
void Push(ST *tt,DataType nn)
//将nn入栈到tt所指栈 (栈中top指向尚未赋值结点)
{
NN *p;
p = (NN *)malloc(sizeof (NN));
tt->top->data = nn;
p->pro = tt->top;
(tt->top)->next = p;
tt->top = p;
tt->size++;
}
int Pop(ST *tt)//出栈
{
NN *p;
if (tt->size==0)
{
printf ("\n\t\t对不起,此栈已空!\n");
getch();
return 0;
}
else
{
printf("\n\t\t栈顶元素为 %d \n",tt->top->pro->data);//%d
p = tt->top;
tt->top = tt->top->pro;
free(p);
tt->top->next=NULL;
if (!(tt->top->next))
{
tt->size--;
printf("\n\t\t出栈成功!栈中尚有%d个元素!按任意键继续...\n",tt->size);
getch();
}
return 1;
}
}
void Show(ST tt)//显示 所有出栈
{
system("cls");
do
{
if (!tt.size)
break;
else
Pop(&tt);
}while(1);
printf("\n\t\t马舒阳报告完毕完毕!按任意键继续...\n");
getch();
}
void change()//数值转换
{
ST cc;
NN *p;
int i,nn,zz,yy,tem_1,tem_2,tem_3;
char ch;
Initiate(&cc);
do
{
system("cls");
printf("\n\n\t\t欢迎进入数据转换!\n\n\t\t(请注意:系统暂不支持十以上进制转换!)\n");
printf("\n\n\t\t请输入一种数字! ");
scanf("%d",&nn);//%d
getchar();
printf("\n\n\t\t请问已输入数字是什么进制呢? ");
scanf("%d",&zz);//%d
getchar();
printf("\n\n\t\t请问您想要转换到几进制呢? ");
scanf("%d",&yy);//%d
getchar();
if(zz>10 || yy>10)
{
printf("\n\t\t待转换数字进制输入不合理!按任意键回到主菜单...");
getch();
return ;
}
if(zz!=10)//若不是十进制 要转换成十进制
{
tem_3=1;//变量含义:进制数n次方
tem_2=0;//变量含义:暂时存储和
tem_1=1;//变量含义:各项数
for(i=0;nn;nn/=10)
{
tem_1=(nn%10)*tem_3 ;
tem_2+=tem_1;
tem_3*=zz;
}
nn=tem_2;
}
for(;nn;nn/=yy)//大除法入栈
{
if(nn%yy<zz)
Push(&cc,nn%yy);
else
{
printf("\n\t\t待转换数字进制输入不合理!按任意键回到主菜单...");
getch();
return ;
}
}
printf("\n\n\t\t转换成果为 ");
for(;cc.base!=cc.top;)//出栈
{
p = cc.top->pro;
printf("%d",p->data);//%d
cc.top = p;
free(p->next);
cc.size--;
}
do
{
printf("\n\n\t\t继续?<Y or N> ");
ch = getchar();
getchar();
if(ch != 'N' && ch != 'Y')
printf("\n\t\t请输入 Y 或 N !\n");
else
break;
}while(1);
}while (ch == 'Y');
}
4、 运营成果
欢迎界面,如图所示。
图1-1
按任意键继续后进入主菜单,选取菜单号1,进入入栈模块,如图所示。
图1-2
开始入栈,输入新栈顶元素(整型),并输入Y或N选取与否继续,此过程中,输入错误有提示,如图所示,以1,3,5,7,9,2,4,6,8,入栈为例。
图1-3
图1-4
图1-5
选取N,输入结束,然后回到主菜单,下面选取菜单号2,进入出栈模块。
图1-6
按任意键继续后,回到主菜单,选取菜单号3,显示栈内剩余信息。
图1-7
图1-8
其间,每一次输出可按需要按任意键输出,并显示剩余信息。
图1-9
图1-10
报告完毕后,即栈已空,按任意键返回到主函数,选取菜单号4 ,进入数制转换模块。
图1-11
输入被转换数字,被转换数字数制及预期数制,并可按需求输入Y或N选取继续或退出。
图1-12
图1-13
退出后返回主菜单,选取0,即可退出程序
。
图1-14
图1-15
四、题目二设计过程
1、题目分析
本题规定建立链表,以存储联系人信息,并设计出对其建立,插入删除显示等基本操作即可。
2、 算法描述
一方面定义一种链表结点构造体,指针域涉及一种next指针,数据域涉及个人姓名及联系方式。
欢迎界面后,进入主菜单,主菜单用switch设计,其中调用函数NUM,该函数可返回有效菜单号,可屏蔽并提示错误信息及重新输入,菜单下调用了其她功能函数,菜单内除退出和初始化函数外所有功能函数均存储在Fx.c.下。
下面仅详细阐述一下各功能模块工作原理。
函数Build,一方面判断该表与否已建立过,即表内与否有一种空结点(头结点),表未初始化时便建立一种空表,否则提示“表已存在,无需建立”。提示后延时2
s自动跳转到主菜单。
插入函数Insert,一方面输入有效信息,然后运用头插法将其插入到头指针下一种结点,再输出提示,提示顾客选取N或Y,判断与否继续,若要继续,则递归本函数,否,直接返回主菜单。
删除函数Delete,一方面判断表与否为空,表为空时,不容许删除,并弹出提示,按任意键继续后后跳转到主菜单;表非空时,输入要删除人姓名,运用循环查找表中人信息(暂不支持多元素查找与删除),若查找成功则输出提示,询问与否拟定删除,按需求,删除该结点(暂不支持误删恢复)或取消操作;若查找失败,不存在该联系人,则输出提示。最后按任意键退回到主菜单。
查询函数Search,一方面判断表与否为空,表为空时,不容许查找,并弹出提示,按任意键继续后后跳转到主菜单;表非空时,输入要查询人姓名,运用循环查找表中人信息(暂不支持多元素查找),然后输出信息,按任意键退回到主菜单。 退出函数Exit,先输出表内所有信息,信息输出完毕后,按任意键结束程序。
3、源代码
MSY.h:
#ifndef MSY_H
#define MSY_H
#include <stdlib.h>
#include <stdio.h>
//#include <conio.h>
#include <windows.h>
#define N 20
typedef struct Node
{
char name[N];
char num[N];
struct Node *next;
}NODE;
void Welcome();
void jiemian();
int Num();
void Build(NODE **head);
void insert(NODE **head);
void Delete(NODE *head);
void Find(NODE *head);
void Exit(NODE *head);
//待改进:多元素查询
//待改进:当head没有初始化,要直接关闭,不容许进行插入和删除等操作
#endif
Fx.c:
#include "MSY.h"
void jiemian()
{
static NODE *head=NULL;
system("cls");
printf("\n\n\t\t\t\t通讯录管理系统\n");
printf("****************************************************\n");
printf("* 1 ……通讯录单链表建立 *\n");
printf("* 2 ……通讯者插入 *\n");
printf("* 3 ……通讯者删除 *\n");
printf("* 4 ……通讯者查询 *\n");
printf("* 0 ……退出 *\n");
printf("****************************************************\n");
printf("\t提示:在2,3,4功能执行前,须先执行1.操作! *\n");
printf("****************************************************\n");
switch(Num())
{
case 1:
Build(&head);
break;
case 2:
insert(&head);
break;
case 3:
Delete(head);
break;
case 4:
Find(head);
break;
case 0:
Exit(head);
break;
}
}
int Num()
{
int k;
printf("\n\t\t请选取菜单号(0…4):");
scanf("%d",&k);
getchar();
if(k<0||k>4)
{
printf("\n\t\t输入错误!按任意键继续...");
getch();
system("cls");
jiemian();
}
else
return k;
}
void Build(NODE **head)
//建立一种有头结点链表(以头结点与否已存在为鉴定根据)
{
system("cls");
if((*head)!=NULL)
{
printf("\n\n\n\n****链表已存在,无需创立!************\n");
}
else
{
(*head)=(NODE *)malloc(sizeof(NODE));
if( (*head) )
{
(*head)->next=NULL;
printf("\n\n##################################################\n");
printf("# -------- 创立成功! -------- #\n");
printf("######################################################\n");
}
else
printf("\t\t内存分派失败!");
}
Sleep();
jiemian();
}
void insert(NODE **head)
{
char ch;
NODE *p;
system("cls");
printf("####################################################\n");
printf("#---------------INSERT NEW CONTACT-----------#\n");
printf("####################################################\n");
p=(NODE *)malloc(sizeof(NODE));
printf("\n\t\t请输入新联系人姓名(1~%d位字母或数字):",N-1);//待改进 鉴定溢出 及 字符或是数字
scanf("%s",&(p->name));
printf("\n\n\t\t请输入新联系人电话号码(1~%d位数字):",N-1);
scanf("%s",&(p->num) );
getchar();
p->next=(*head)->next;
(*head)->next=p;
if(p==(*head)->next)
{
printf("\n\n================= 插入成功!==============\n");
}
else
{
printf("\n\n================= 插入失败!================\n");
}
Sleep(1500);
do
{
system("cls");
printf("#######################################################\n");
printf("#######################################################\n");
printf("\n\n\t\t与否继续?<Y or N> ");
ch=getchar();
getchar();
if(ch!='N' && ch!='Y')
{
printf("\n\t\t输入有误,按任意键继续");
getchar();
}
else
{
if(ch=='Y')
insert(head);
break;
}
}while(1);
jiemian();
}
void Delete(NODE *head)
{
NODE *n,*p;
char ch,name[N];
system("cls");
printf("##################################################\n");
printf("#-----------------------DELETE----------------------#\n");
printf("####################################################\n");
if(!(head->next))
{
printf("\n\n\n\n\t******通讯录为空!快加入新联系人吧!****\n");
printf("\n\t\t按任意键继续...");
getch();
jiemian();
}
printf("\n\n\t\t请输入欲删除联系人姓名:");
scanf("%s",name);
getchar();
p=head;
do
{
if(!strcmp(p->name,name))
break;
else
{
n=p;
p=p->next;
}
}while(p);
if(!p)
printf("\n\n------您所输入联系人不存在,请查证!--------\n");
else
{
printf("\n\n\t\tTA电话号码是%s,您拟定要删除吗?<Y or N> ",p->num);
scanf("%c",&ch);
getchar();
if(ch!='Y' && ch !='N')
{
printf("\n\t\t输入错误!按任意键继续...");
getch();
}
else if(ch=='N')
printf("\n\n--------删除未成功!-------- \n");
else
{
n->next=p->next;
free(p);
printf("\n\n -------- 删除成功! -------- \n");
}
}
printf("\n\t\t按任意键继续...");
getch();
jiemian();
}
void Find(NODE *head)
{
NODE *p;
char name[N];
system("cls");
printf("####################################################\n");
printf("#---------------------SEARCH-----------------------#\n");
printf("#####################################################\n");
if(!(head->next))
{
printf("\n\n\n\n******通讯录为空!快加入新联系人吧!*****\n");
printf("\n\t\t按任意键继续...");
getch();
jiemian();
}
printf("\n\n\t\t请输入TA姓名:");
scanf("%s",name);
getchar();
p=head;
while(p)
{
if(!strcmp(name,p->name))
break;
p=p->next;
}
if(p)
printf("\n\t\tTA电话号码为%s!\n",p->num);
else
展开阅读全文