源码自取:
//file.h
#ifndef _FILE
#define _FILE
#include "student.h"
int createFile(Student *stu);
int readFile(Student *stu);
void saveFile(Student *stu,int n);
#endif
//file.c
#include<stdio.h>
#include<stdlib.h>
#include"student.h"
#include"file.h"
int readFile(Student *stu)
{
FILE *fp;
int i=0;
if((fp=fopen("d:\\student.dat","rb"))==NULL)
{
printf("file does not exist,creat it first:\n");
return 0;
}
fread(&stu[i],sizeStu,1,fp);
while(!feof(fp))
{
i++;
fread(&stu[i],sizeStu,1,fp);
}
fclose(fp);
return i;
}
void saveFile(Student *stu,int n)
{
FILE *fp;
if((fp=fopen("d:\\student.dat","wb"))==NULL)
{
printf("can ont open file!\n");
exit (0);
}
fwrite(stu,sizeStu,n,fp);
fclose(fp);
}
int creatFile(Student *stu)
{
FILE *fp;
int n;
if((fp=fopen("d:\\student.dat","wb"))==NULL)
{
printf("can not open file!\n");
exit(0);
}
printf("input students\' information:\n");
n=readStu(stu,NUM);
fwrite(stu,sizeStu,n,fp);
fclose(fp);
return n;
}
//student.h
#ifndef _STUDENT
#define _STUDENT
#define NUM 20
struct Student
{
long num;
char name[20];
char sex[10];
int score[3];
int total;
int rank;
};
typedef struct Student Student; /*定义类型的别名Student*/
#define sizeStu sizeof(Student) /*一个学生记录所需要的内存空间大小*/
int readStu(Student *stu,int n); //读入学生记录,学号为0或者读满停止
void printStu(Student *stu,int n); // 屏幕输出所有学生记录的值
int equal(Student sl,Student s2,int condition); //根据condition判断s1与s2相等否
int larger(Student sl,Student s2,int condition); //根据condition比较s1与s2的大小
void reverse(Student *stu,int n); //学生记录数组元素逆置
void calcuTotal(Student *stu,int n); //计算所有学生的总分
void calcuRank(Student *stu,int n); //根据总分计算学生的名次级并列
void calcuMark(double m[3][3],Student *stu,int n); //求3门课的最高分、最低分、平均分
void sortStu(Student *stu,int n,int condition); //根据条件用选择法从小到大排序
int searchStu(Student *stu,int n,Student s,int condition,int *f); //根据条件查找数组
int insertStu(Student *stu,int n,Student s); //向数组中插入一个元素按照学号有序存放
int deleteStu(Student *stu,int n,Student); //从数组中删除 一个指定学号元素
#endif
//student.c
#include"student.h"
#include<stdio.h>
#include<string.h>
/*函数功能:从键盘读入学生的初始值
函数参数:2个形式参数分别为结构体指针和预设记录条数
函数返回值:从键盘上实际读入的记录条数*/
int readStu(Student *stu,int n)
{
int i,j;
for(i=0;i<n;i++)
{
printf("Input one student\'s information");
printf("num: ");
scanf("%ld",&stu[i].num);
if(stu[i].num==0) break;
printf("name: ");
scanf("%s",stu[i].name);
printf("sex: ");
scanf("%s",stu[i].sex);
stu[i].total=0; //总分需要计算求得,初值置为0
printf("Input three course of the student:\n");
for(j=0;j<3;j++)
stu[i].rank=0; //名次要根据总分计算,初值置为0
}
return i; //返回实际读入的记录条数
}
/*函数功能:输出所有学生记录的值
函数参数:2个形式参数分别为结构体指针和记录条数
函数返回值:无返回值*/
void printStu(Student *stu,int n)
{
int i,j;
for(i=0;i<n;i++)
{
printf("%81ld",stu[i].num);
printf("%8s",stu[i].name);
printf("%8s",stu[i].sex);
for(j=0;j<3;j++)
printf("%6d",stu[i].score[j]);
printf("%7d",stu[i].total);
printf("%5d\n",stu[i].rank);
}
}
/*函数功能:判断两个Student记录是否相等
函数参数“3个形式参数分别为待比较的两个结构体变量比较条件
函数返回值:比较结果,相等返回1,不相等返回0*/
int equal(Student s1,Student s2,int condition)
{if(condition==1) //如果参数condition的值为1,则比较学号
return s1.num==s2.num; //如果参数condition的值为2,则比较姓名
else if(condition==2)
{
if(strcmp(s1.name,s2.name)==0)
return 1;
else return 0;
}
else if(condition==3) //如果参数condition的值为3,则比较名次
return s1.rank==s2.rank; //如果参数condition的值为4,则比较总分
else if(condition==4)
return s1.total==s2.total;
else return 1;
}
/*函数功能:比较两个Student记录的大小
函数参数:3个形式参数分别为待比较的两个结构体变量及比较条件
函数返回值:比较的结果,第一个记录大于第2个则返回1,否则返回0*/
int larger(Student s1,Student s2,int condition)
{
if (condition==1)
return s1.num>s2.num;
else if(condition==2)
return s1.total>s2.total;
else return 1;
}
/*函数功能:数组的元素逆置
函数参数:2个形式参数分别为结构体指针和记录条数
函数返回值:无返回值*/
void reverse(Student *stu,int n)
{
int i;
Student temp;
for(i=0;i<n/2;i++)
{
temp=stu[i];
stu[i]=stu[n-1-i];
stu[n-1-i]=temp;
}
}
/*函数功能:计算所有学生总分
函数参数:2个形式参数分别为结构体指针和记录条数
函数返回值;无返回值*/
void calcuTotal(Student *stu,int n)
{
int i,j;
for(i=0;i<3;i++)
{
stu[i].total=0;
for(j=0;j<3;j++)
stu[i].total+=stu[i].score[j];
}
}
/*函数功能:根据总分计算排名,同分同名次
函数参数:2个形参数分别为结构体指针和记录条数
函数返回值:无返回值*/
void calcuRank(Student *stu,int n)
{
int i;
sortStu(stu,n,2);
reverse(stu,n);
stu[0].rank=1;
for(i=1;i<n;i++)
{
if(equal(stu[i],stu[i-1],4))
stu[i].rank=stu[i-1].rank;
else
stu[i].rank=i+1;
}
}
/*函数功能:求3门课的最高分,最低分,平均分
函数参数:第1个形式参m第1维代表3门课,第二维代表最高分、最低分、平均分,第2个形参是结构体指针,第3个形式参是记录条数
函数返回值:无返回值*/
void calcuMark(double m[3][3],Student stu[],int n)
{
int i,j;
for(i=0;i<3;i++)
{
m[i][0]=stu[0].score[i];
for(j=1;j<n;j++)
if(m[i][0]<stu[j].score[i])
m[i][0]=stu[j].score[i];
}
for(i=0;i<3;i++)
{
m[i][2]=stu[0].score[i];
for(j=1;j<n;j++)
m[i][2]+=stu[j].score[i];
m[i][2]/=n;
}
}
/*函数功能:按照condition规定的条件由小到大排序
函数参数:2个形象分别是结构指针、记录条数、排序依据的条件
函数返回值;无返回值*/
void sortStu(Student *stu,int n,int condition)
{
int i,j,minpos;
Student t;
for(i=0;i<n-1;i++)
{
minpos=i;
for(j=i+1;j<n;j++)
if(larger(stu[minpos],stu[j],condition))
minpos=j;
if(i!=minpos)
{
t=stu[i];
stu[i]=stu[minpos];
stu[minpos]=t;
}
}
}
/*函数功能:按照condition规定的条件,查找指定记录是否存在
函数参数:5个形参粉呗是结构体指针、记录条数、待查找的记录、查找条件,查找到的多个元素应下标所存放的数组f
函数返回值:查找到的记录条数*/
int searchStu(Student *stu,int n,Student s,int condition,int *f[])
{
int i,j=0,find=0;
for(i=0;i<n;i++)
if(equal(stu[i],s,condition))
{
f[j++]=i;
find++;
}
return find;
}
/*函数功能:向结构体数组中依学号递增插入一条记录
函数参数:3个形参分别是结构体指针、原来的记录条数、待插入的记录
函数返回值i:插入后的实际记录条数*/
int insertStu(Student *stu,int n,Student s)
{
int i;
sortStu(stu,n,1);
for(i=0;i<n;i++)
if(equal(stu[i],s,1))
{printf("this record exist,can not insert again!\n");
return n;
}
for(i=n-1;i>=0;i--)
{
if(!larger(stu[i],s,1))
break;
stu[i+1]=stu[i];
}
stu[i+1]=s;
n++;
return n;
}
/*函数功能:从结构体中删除指定学号的一条记录
函数参数: 3个形参分别是结构体指针、原来的记录条数、待删除的记录
函数返回值:删除后的实际记录条数*/
int deleteStu(Student *stu,int n,Student s)
{
int i,j;
for(i=0;i<n;i++)
if(equal(stu[i],s,1)) break;
if(i==n)
{
printf("this record does not exsit!\n");
return n;
}
for(j=i;j<n-1;j++)
stu[j]=stu[j+1];
n--;
return n;
}
//menu.h
#ifndef _MENU
#define _MENU
void menu();
void menuBase();
void menuScore();
void menuCount();
void menuSearch();
#endif
//menu.c
#include<stdio.h>
#include"menu.h"
void menu()
{
printf("******1.显示基本信息******\n");
printf("******2.基本信息管理******\n");
printf("******3.学生成绩管理******\n");
printf("******4.考试成绩统计******\n");
printf("******5.根据条件查询******\n");
printf("******0.退出******\n");
}
void menuBase()
{
printf("******1.插入学生记录******\n");
printf("******2.删除学生记录******\n");
printf("******3.修改学生记录******\n");
printf("******4.返回上层菜单******\n");
}
void menuScore()
{
printf("******1.计算学生总分j******\n");
printf("******2.根据总分排名******\n");
printf("******3.返回上层菜单******\n");
}
void menuCount()
{
printf("******1.求课程最高分******\n");
printf("******2.求课程最低分******\n");
printf("******3.求课程平均分******\n");
printf("******4.返回上层菜单******\n");
}
void menuSearch()
{
printf("******1.按学号查询******\n");
printf("******2.按姓名查询******\n");
printf("******3.按名次查询******\n");
printf("******4.返回上层菜单******\n");
}
//manage.h
#ifndef _MAINCONTROL
#define _MAINCONTROL
void printHead();
int baseManage(Student *stu,int n);
void scoreManage(Student *stu,int n);
void printMarkCourse(char *s,double m[3][3],int k);
void countManage(Student *stu,int n);
void searchManage(Student *stu,int n);
int runMain(Student *stu,int n,int choice);
#endif
//manage.c
#include<stdio.h>
#include<string.h>
#include"file.h"
#include"menu.h"
#include"student.h"
#include"mainControl.h"
void printHead()
{
printf("%8s%10s%8s%6s%6s%8s%6s%6s\n","学号","姓名","性别","数学","英语","计算机","总分","名次");
}
int baseManage(Student *stu,int n)
{
int choice,t,find[NUM];
Student s;
do
{
menuBase();
printf("choose one opration you want to do:\n");
scanf("%d",&choice);
switch(choice)
{
case 1: readStu(&s,1);
n=insertStu(stu,n,s);
break;
case 2: printf("Input the number deleted\n");
scanf("%ld",&s.num);
n=deleteStu(stu,n,s);
break;
case 3: printf("Input the number modified\n");
scanf("%ld",&s.num);
t=searchStu(stu,n,s,1,find);
if (t)
{
readStu(&s,1);
stu[find[0]]=s;
}
else
printf("this student is not in,can not be modified.\n");
break;
case 0: break;
}
}while(choice);
return n;
}
void scoreManage(Student *stu,int n)
{
int choice;
do
{
menuScore();
printf("choose one operation you want to do:\n");
scanf("%d",&choice);
switch(choice)
{
case 1: calcuTotal(stu,n);break;
case 2: calcuRank(stu,n);break;
case 0: break;
}
} while (choice);
}
void printMarkCourse(char *s,double m[3][3],int k)
{
int i;
printf("%s",s);
for(i=0;i<3;i++)
printf("%10.21f",m[i][k]);
printf("\n");
}
void countManage(Student *stu,int n)
{
int choice;
double mark[3][3];
do
{
menuCount();
calcuMark(mark,stu,n);
printf("choose one operation you want to do:\n");
scanf("%d",&choice);
switch(choice)
{
case 1: printMarkCourse("highest:\n",mark,0);
break;
case 2: printMarkCourse("lowest:\n",mark,1);
break;
case 3: printMarkCourse("average:\n",mark,2);
break;
case 0: break;
}
}while(choice);
}
void searchManege(Student *stu,int n)
{
int i,choice,findnum,f[NUM];
Student s;
do
{
menuSearch();
printf("choose one opration you want to do:\n");
scanf("%d",&choice);
switch(choice)
{
case 1: printf("Input a student\'s num will be searched:\n");
scanf("%ld",&s.num);
break;
case 2: printf("Input a student\'s num will be searched:\n");
scanf("%s",s.name);
break;
case 3: printf("Input a rank will be searched:\n");
scanf("%d",&s.rank);
break;
case 0: break;
}
if(choice>=1&&choice<=3)
{
findnum=searchStu(stu,n,s,choice,f);
if(findnum)
{
printHead();
for(i=0;i<=findnum;i++)
printStu(&stu[f[i]],1);
}
else
printf("this record does not exist!\n");
}
}while(choice);
}
int runMain(Student *stu,int n,int choice)
{
switch(choice)
{
case 1: printHead();
sortStu(stu,n,1);
printStu(stu,n);
break;
case 2: n=baseManage(stu,n);
break;
case 3: scoreManage(stu,n);
break;
case 4: countManage(stu,n);
break;
case 5: searchManege(stu,n);
break;
case 0: break;
}
return n;
}
int main()
{
Student stu[NUM];
int choice,n;
n=readFile(stu);
if(!n)
n=createFile(stu);
do
{
menu();
printf("please input your choice:");
scanf("%d",&choice);
if(choice>=0&&choice<=5)
n=runMain(stu,n,choice);
else
printf("erro input,please inpout your choice again!\n");
}while(choice);
sortStu(stu,n,1);
saveFile(stu,n);
return 0;
}