|
|
#include<stdio.h>
|
|
|
#include<stdlib.h>
|
|
|
#include<string.h>
|
|
|
int save=0;
|
|
|
struct student /*构建结构体*/
|
|
|
{
|
|
|
char num[12];
|
|
|
char name[20] ;
|
|
|
char sex[4] ;
|
|
|
int CYuYan;
|
|
|
int Math;
|
|
|
int English;
|
|
|
int sum;
|
|
|
int ave;
|
|
|
} ;
|
|
|
typedef struct node
|
|
|
{
|
|
|
struct student data;
|
|
|
struct node *next;
|
|
|
} Node, *Link;
|
|
|
void Menu() /*界面主菜单*/
|
|
|
{
|
|
|
printf("******************\n") ;
|
|
|
printf("\t1输入学生资料\t\t\t\t\t2删除学生资料\n") ;
|
|
|
printf("\t3查询学生成绩\t\t\t\t\t4修改学生成绩\n") ;
|
|
|
printf("\t5显示学生资料\t\t\t\t\t6统计学生资料\n") ;
|
|
|
printf("\t7排序学生成绩\t\t\t\t\t8保存学生成绩\n") ;
|
|
|
printf("\t9退出系统\n") ;
|
|
|
printf("**********************") ;
|
|
|
}
|
|
|
void Print()
|
|
|
{
|
|
|
printf("--------------------") ;
|
|
|
}
|
|
|
void Wrong() /*错误警告*/
|
|
|
{
|
|
|
printf("\n警告: 输入错误! !!\n") ;
|
|
|
}
|
|
|
void Nofind()
|
|
|
{
|
|
|
printf("\n警告: 没有找到该学生! !! \n") ;
|
|
|
}
|
|
|
void Print1()
|
|
|
{
|
|
|
printf(" 学号\t 姓名 性别 C语言成绩 英语成绩 数学成绩 总分 平均分\n") ;
|
|
|
}
|
|
|
void Print2(Node *p) /*打印学生成绩*/
|
|
|
{
|
|
|
printf("%-9s%s\t%3s\t%d\t%d\t%d\t %d\t %d\n", p->data.num, p->data.name, p->data.sex, p->data.CYuYan, p->data.Math, p->data.English, p->data.sum, p->data.ave);
|
|
|
}
|
|
|
Node *Locate(Link h, char findmess[], char nameornum[] ) /*定位链表中符合要求的接点*/
|
|
|
{
|
|
|
Node *r;
|
|
|
if(strcmp(nameornum, "num") ==0) /*按学号查询*/
|
|
|
{
|
|
|
r=h->next;
|
|
|
while(r!=NULL)
|
|
|
{
|
|
|
if(strcmp(r->data. num, findmess) ==0)
|
|
|
return r;
|
|
|
r=r->next;
|
|
|
}
|
|
|
}
|
|
|
else if(strcmp(nameornum, "name") ==0) /*按姓名查询*/
|
|
|
{
|
|
|
r=h->next;
|
|
|
while(r!=NULL)
|
|
|
{
|
|
|
if(strcmp(r->data. name, findmess) ==0)
|
|
|
return r;
|
|
|
r=r->next;
|
|
|
}
|
|
|
}
|
|
|
return 0;
|
|
|
}
|
|
|
void Add(Link h) /*功能1: 输入学生资料*/
|
|
|
{
|
|
|
Node *p, *r, *s;
|
|
|
char num[12];
|
|
|
r=h;
|
|
|
s=h->next;
|
|
|
while(r->next!=NULL)
|
|
|
r=r->next;
|
|
|
while(1)
|
|
|
{
|
|
|
printf("请输入学号(按' 0' 返回上菜单) : ") ;
|
|
|
scanf("%s", num) ;
|
|
|
if(strcmp(num, "0") ==0)
|
|
|
break;
|
|
|
p=(Node *) malloc(sizeof(Node) ) ; /*申请一个结构体内存*/
|
|
|
strcpy(p->data. num, num) ;
|
|
|
printf("请输入姓名: ") ;
|
|
|
scanf("%s", p->data. name) ;
|
|
|
getchar() ;
|
|
|
printf("请输入性别: ") ;
|
|
|
scanf("%s", p->data. sex) ;
|
|
|
getchar() ;
|
|
|
printf("请你输入c语言成绩: ") ;
|
|
|
scanf("%d", &p->data. CYuYan) ;
|
|
|
getchar() ;
|
|
|
printf("请输入数学成绩: ") ;
|
|
|
scanf("%d", &p->data. Math) ;
|
|
|
getchar() ;
|
|
|
printf("请输入英语成绩: ") ;
|
|
|
scanf("%d", &p->data. English) ;
|
|
|
getchar() ;
|
|
|
p->data. sum=p->data. English+p->data. CYuYan+p->data. Math;
|
|
|
p->data. ave=p->data. sum / 3;
|
|
|
p->next=NULL;
|
|
|
r->next=p;
|
|
|
r=p;
|
|
|
save=1;
|
|
|
}
|
|
|
}
|
|
|
void Del(Link h) /*功能2: 删除学生资料*/
|
|
|
{
|
|
|
Node *p, *r;
|
|
|
char findmess[20];
|
|
|
printf("请输入要删除的学号: ") ;
|
|
|
scanf("%s", findmess) ;
|
|
|
p=Locate(h, findmess, "num");
|
|
|
if(p)
|
|
|
{
|
|
|
r=h;
|
|
|
while(r->next!=p)
|
|
|
r=r->next;
|
|
|
r->next=p->next;
|
|
|
free(p) ; /*释放内存空间
|
|
|
*/
|
|
|
printf("\n提示: 该学生已经成功删除! \n") ;
|
|
|
save=1;
|
|
|
}
|
|
|
else
|
|
|
Nofind() ;
|
|
|
}
|
|
|
void Cha(Link h) /*功能3: 查询学生资料*/
|
|
|
{
|
|
|
int sel;
|
|
|
char findmess[20];
|
|
|
Node *p;
|
|
|
printf("\n1按学号查找\n2按姓名查找\n") ;
|
|
|
scanf("%d", &sel) ;
|
|
|
if(sel==1) /*按学号查找*/
|
|
|
{
|
|
|
printf("请输入要查找的学号: ") ;
|
|
|
scanf("%s", findmess) ;
|
|
|
p=Locate(h, findmess, "num") ;
|
|
|
if(p)
|
|
|
{
|
|
|
printf("\t\t\t\t查找结果\n") ;
|
|
|
Print() ;
|
|
|
Print1() ;
|
|
|
Print2(p) ;
|
|
|
Print() ;
|
|
|
}
|
|
|
else
|
|
|
Nofind() ;
|
|
|
}
|
|
|
else if(sel==2) /*按姓名查找*/
|
|
|
{
|
|
|
printf("请输入要查找的姓名: ") ;
|
|
|
scanf("%s", findmess) ;
|
|
|
p=Locate(h, findmess, "name");
|
|
|
if(p)
|
|
|
{
|
|
|
printf("\t\t\t\t查找结果\n") ;
|
|
|
Print() ;
|
|
|
Print1() ;
|
|
|
Print2(p) ;
|
|
|
Print() ;
|
|
|
}
|
|
|
else
|
|
|
Nofind() ;
|
|
|
}
|
|
|
else
|
|
|
Wrong() ;
|
|
|
}
|
|
|
void Change(Link h) /*功能4: 修改学生资料*/
|
|
|
{
|
|
|
Node *p;
|
|
|
char findmess[20];
|
|
|
if(!h->next)
|
|
|
{
|
|
|
printf("\n提示: 没有资料可以修改!\n") ;
|
|
|
return;
|
|
|
}
|
|
|
printf("请输入要修改的学生学号: ") ;
|
|
|
scanf("%s", findmess) ;
|
|
|
p=Locate(h, findmess, "num");
|
|
|
if(p)
|
|
|
{
|
|
|
printf("请输入新学号(原来是%s) : ", p->data. num) ;
|
|
|
scanf("%s", p->data. num) ;
|
|
|
printf("请输入新姓名(原来是%s) : ", p->data. name) ;
|
|
|
scanf("%s", p->data. name) ;
|
|
|
getchar() ;
|
|
|
printf("请输入新性别(原来是%s) : ", p->data. sex) ;
|
|
|
scanf("%s", p->data. sex) ;
|
|
|
printf("请输入新的c语言成绩(原来是%d分) : ", p->data. CYuYan) ;
|
|
|
scanf("%d", &p->data. CYuYan) ;
|
|
|
getchar() ;
|
|
|
printf("请输入新的数学成绩(原来是%d分) : ", p->data. Math) ;
|
|
|
scanf("%d", &p->data. Math) ;
|
|
|
getchar() ;
|
|
|
printf("请输入新的英语成绩(原来是%d分) : ", p->data. English) ;
|
|
|
scanf("%d", &p->data. English) ;
|
|
|
p->data. sum=p->data. English+p->data. CYuYan+p->data. Math;
|
|
|
p->data. ave=p->data. sum/3;
|
|
|
printf("\n提示: 资料修改成功!\n") ;
|
|
|
save=1;
|
|
|
}
|
|
|
else
|
|
|
Nofind() ;
|
|
|
}
|
|
|
void Disp(Link h) /*功能5: 显示学生资料*/
|
|
|
{
|
|
|
int count=0;
|
|
|
Node *p;
|
|
|
p=h->next;
|
|
|
printf("\t\t\t\t显示结果\n") ;
|
|
|
Print() ;
|
|
|
Print1() ;
|
|
|
printf("\n") ;
|
|
|
while(p)
|
|
|
{
|
|
|
Print2(p) ;
|
|
|
p=p->next;
|
|
|
}
|
|
|
Print() ;
|
|
|
printf("\n") ;
|
|
|
}
|
|
|
void Tongji(Link h) /*功能6: 统计学生成绩*/
|
|
|
{
|
|
|
float jige1, jige2, jige3, i=0;
|
|
|
int
|
|
|
A1=0, A2=0, A3=0, B1=0, B2=0, B3=0, C1=0, C2=0, C3=0, D1=0, D2=0, D3=0, E1=0, E2=
|
|
|
0, E3=0;
|
|
|
Node *pm, *pe, *pc, *ps, *pa; /*用于指向分数最高的接点*/
|
|
|
Node *r=h->next;
|
|
|
pm=pe=pc=ps=pa=r;
|
|
|
while(r!=NULL)
|
|
|
{
|
|
|
if(r->data. CYuYan>=pc->data. CYuYan)
|
|
|
pc=r;
|
|
|
if(r->data. Math>=pm->data. Math)
|
|
|
pm=r;
|
|
|
if(r->data. English>=pe->data. English)
|
|
|
pe=r;
|
|
|
if(r->data. sum>=ps->data. sum)
|
|
|
ps=r;
|
|
|
if(r->data. ave>=pa->data. ave)
|
|
|
pa=r;
|
|
|
r=r->next;
|
|
|
}
|
|
|
r=h;
|
|
|
while(r!=NULL)
|
|
|
{
|
|
|
switch(r->data. CYuYan/10)
|
|
|
{
|
|
|
case 10:
|
|
|
case 9:
|
|
|
A1++;
|
|
|
break;
|
|
|
case 8:
|
|
|
B1++;
|
|
|
break;
|
|
|
case 7:
|
|
|
C1++;
|
|
|
break;
|
|
|
case 6:
|
|
|
D1++;
|
|
|
break;
|
|
|
case 5:
|
|
|
case 4:
|
|
|
case 3:
|
|
|
case 2:
|
|
|
case 1:
|
|
|
case 0:
|
|
|
E1++;
|
|
|
break;
|
|
|
}
|
|
|
i++;
|
|
|
r=r->next;
|
|
|
}
|
|
|
jige1=(A1+B1+C1+D1) /(i-1) ;
|
|
|
r=h, i=0;
|
|
|
while(r!=NULL)
|
|
|
{
|
|
|
switch(r->data. Math/10)
|
|
|
{
|
|
|
case 10:
|
|
|
case 9:
|
|
|
A2++;
|
|
|
break;
|
|
|
case 8:
|
|
|
B2++;
|
|
|
break;
|
|
|
case 7:
|
|
|
C2++;
|
|
|
break;
|
|
|
case 6:
|
|
|
D2++;
|
|
|
break;
|
|
|
case 5:
|
|
|
case 4:
|
|
|
case 3:
|
|
|
case 2:
|
|
|
case 1:
|
|
|
case 0:
|
|
|
E2++;
|
|
|
break;
|
|
|
}
|
|
|
i++;
|
|
|
r=r->next;
|
|
|
}
|
|
|
jige2=(A2+B2+C2+D2) /(i-1) ;
|
|
|
r=h, i=0;
|
|
|
while(r!=NULL)
|
|
|
{
|
|
|
switch(r->data. English/10)
|
|
|
{
|
|
|
case 10:
|
|
|
case 9:
|
|
|
A3++;
|
|
|
break;
|
|
|
case 8:
|
|
|
B3++;
|
|
|
break;
|
|
|
case 7:
|
|
|
C3++;
|
|
|
break;
|
|
|
case 6:
|
|
|
D3++;
|
|
|
break;
|
|
|
case 5:
|
|
|
case 4:
|
|
|
case 3:
|
|
|
case 2:
|
|
|
case 1:
|
|
|
case 0:
|
|
|
E3++;
|
|
|
break;
|
|
|
}
|
|
|
i++;
|
|
|
r=r->next;
|
|
|
}
|
|
|
jige3=(A3+B3+C3+D3) /(i-1) ;
|
|
|
printf("------------------------------统计结果-------------------------------\n") ;
|
|
|
printf("总分最高者: \t%s %d分\n", ps->data. name, ps->data. sum) ;
|
|
|
printf("平均分最高者: \t%s %d分\n", pa->data. name, pa->data. ave) ;
|
|
|
printf("C语言最高者: \t%s %d分\n", pc->data. name, pc->data. CYuYan) ;
|
|
|
printf("英语最高者: \t%s %d分\n", pe->data. name, pe->data. English) ;
|
|
|
printf("数学最高者: \t%s %d分\n", pm->data. name, pm->data. Math) ;
|
|
|
printf("C语言分数段: \tA: %d人 B: %d人 C: %d人 D: %d人 E: %d人\n", A1, B1, C1, D1, E1) ;
|
|
|
printf("数学分数段: \tA: %d人 B: %d人 C: %d人 D: %d人 E: %d人\n", A2, B2, C2, D2, E2) ;
|
|
|
printf("英语分数段: \tA: %d人 B: %d人 C: %d人 D: %d人 E: %d人\n", A3, B3, C3, D3, E3) ;
|
|
|
printf("C语言及格率: %3. 2f%%\n", jige1*100) ;
|
|
|
printf("数学及格率: %3. 2f%%\n", jige2*100) ;
|
|
|
printf("英语及格率: %3. 2f%%\n", jige3*100) ;
|
|
|
printf("备注: A: 90—100; B: 80—89; C: 70—79; D: 60—69; E: 0—59\n") ;
|
|
|
Print() ;
|
|
|
}
|
|
|
void Sort(Link h) /*功能7: 排序学生成绩*/
|
|
|
{
|
|
|
Link hh;
|
|
|
Node *p, *rr, *s;
|
|
|
hh=(Link) malloc(sizeof(Node) ) ; /*用于做新的链表*/
|
|
|
hh->next=NULL;
|
|
|
if(h->next==NULL)
|
|
|
{
|
|
|
printf("\n提示: 没有资料可以排序!\n") ;
|
|
|
return ;
|
|
|
}
|
|
|
p=h->next;
|
|
|
while(p)
|
|
|
{
|
|
|
s=(Node*) malloc(sizeof(Node) ) ; /*新建接点用于保存信
|
|
|
息*/
|
|
|
s->data=p->data;
|
|
|
s->next=NULL;
|
|
|
rr=hh;
|
|
|
while(rr->next!=NULL && rr->next->data. sum>=p->data. sum)
|
|
|
rr=rr->next;
|
|
|
if(rr->next==NULL)
|
|
|
rr->next=s;
|
|
|
else
|
|
|
{
|
|
|
s->next=rr->next;
|
|
|
rr->next=s;
|
|
|
}
|
|
|
p=p->next;
|
|
|
}
|
|
|
free(h) ; /*释放内存*/
|
|
|
h->next=hh->next;
|
|
|
printf("\n提示: 排序已经完成!\n") ;
|
|
|
}
|
|
|
void Save(Link h) /*功能8: 保存学生资料*/
|
|
|
{
|
|
|
FILE* fp; /*文件指针*/
|
|
|
Node *p;
|
|
|
int flag=1, count=0;
|
|
|
fp=fopen("c: \\student", "wb") ; /*以只读方式打开文件*/
|
|
|
if(fp==NULL)
|
|
|
{
|
|
|
printf("\n提示: 重新打开文件时发生错误!\n") ;
|
|
|
exit(1) ;
|
|
|
}
|
|
|
p=h->next;
|
|
|
while(p)
|
|
|
{
|
|
|
if(fwrite(p, sizeof(Node) , 1, fp) ==1)
|
|
|
{
|
|
|
p=p->next;
|
|
|
count++;
|
|
|
}
|
|
|
else
|
|
|
{
|
|
|
flag=0;
|
|
|
break;
|
|
|
}
|
|
|
}
|
|
|
if(flag)
|
|
|
{
|
|
|
printf("\n提示: 文件保存成功(有%d条记录已经保存) \n", count) ;
|
|
|
save=0;
|
|
|
}
|
|
|
fclose(fp) ; /*关闭文件*/
|
|
|
}
|
|
|
main(void)
|
|
|
{
|
|
|
Link h;
|
|
|
FILE *fp; /*文件指针*/
|
|
|
int sel;
|
|
|
char ch;
|
|
|
char chuangjian;
|
|
|
int count=0;
|
|
|
Node *r;
|
|
|
printf("\t\t\t\t学生成绩管理系统\n") ;
|
|
|
h=(Node*) malloc(sizeof(Node) ) ; /*申请内存*/
|
|
|
h->next=NULL;
|
|
|
r=h;
|
|
|
fp=fopen("C: \\student", "rb") ; /*以只读方式打开文件*/
|
|
|
if(fp==NULL) /*创建新文件*/
|
|
|
{
|
|
|
printf("\n提示: 文件还不存在, 是否创建? (y/n) \n") ;
|
|
|
scanf("%c", &chuangjian) ;
|
|
|
if(chuangjian=='y' || chuangjian=='Y' )
|
|
|
fp=fopen("C: \\student", "wb") ;
|
|
|
else
|
|
|
exit(0) ;
|
|
|
}
|
|
|
printf("\n提示: 文件已经打开, 正在导入记录. . . . . . \n") ;
|
|
|
printf("\n提示: 记录导入完毕, 共导入%d条记录\n", count) ;
|
|
|
while(1)
|
|
|
{
|
|
|
Menu() ;
|
|
|
printf("请选择操作: ") ;
|
|
|
scanf("%d", &sel) ;
|
|
|
if(sel==9)
|
|
|
{
|
|
|
if(save==1)
|
|
|
{
|
|
|
getchar() ;
|
|
|
printf("\n提示: 资料已经改动, 是否将改动保存到文件中(y/n) ?\n") ;
|
|
|
scanf("%c", &ch) ;
|
|
|
if(ch=='y' || ch=='Y' )
|
|
|
Save(h) ;
|
|
|
}
|
|
|
printf("\n提示: 你已经退出系统! \n") ;
|
|
|
break;
|
|
|
}
|
|
|
switch(sel)
|
|
|
{
|
|
|
case 1:
|
|
|
Add(h) ;
|
|
|
break;
|
|
|
case 2:
|
|
|
Del(h) ;
|
|
|
break;
|
|
|
case 3:
|
|
|
Cha(h) ;
|
|
|
break;
|
|
|
case 4:
|
|
|
Change(h) ;
|
|
|
break;
|
|
|
case 5:
|
|
|
Disp(h) ;
|
|
|
break;
|
|
|
case 6:
|
|
|
Tongji(h) ;
|
|
|
break;
|
|
|
case 7:
|
|
|
Sort(h) ;
|
|
|
break;
|
|
|
case 8:
|
|
|
Save(h) ;
|
|
|
break;
|
|
|
default:
|
|
|
Wrong() ;
|
|
|
getchar() ;
|
|
|
break;
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|