大学生成绩管理系统
1.程序的功能
录入学生成绩,
插入学生成绩,
修改学生成绩,
删除学生成绩,
查找学生信息,
显示学生信息,
对学生成绩按总分由高到低进行排序,
统计学生人数;
2.预备知识
排序算法
结构体
switch—case分支语句
按格式输出
磁盘文件的基本操作
malloc申请内存空间
system函数
strcpy函数
3.程序主要函数
void in(); //录入学生成绩信息
void show(); //显示学生成绩信息
void order(); //按总分排序
void del(); //删除学生成绩信息
void modify(); //修改学生成绩信息
void menu(); //主菜单
void insert(); //插入学生成绩信息
void total(); //计算总人数
void search(); //查找学生信息
4.程序演示(编译环境为vs 2013)
录入学生成绩
查找学生信息
删除学生信息
修改学生信息
插入学生信息
排序
统计学生人数
显示所有学生信息
5.源码
头文件stu.h:
/*
结构体
*/
struct student //定义学生成绩结构体
{
int num; //学号
char name[15]; //姓名
double elec; //选修课
double expe; //实验课
double requ; //必修课
double sum; //总分
};
struct student stu[50]; //定义结构体数组
/*
函数声明
*/
void in(); //录入学生成绩信息
void show(); //显示学生成绩信息
void order(); //按总分排序
void del(); //删除学生成绩信息
void modify(); //修改学生成绩信息
void menu(); //主菜单
void insert(); //插入学生成绩信息
void total(); //计算总人数
void search(); //查找学生信息
源文件stu.c:
#include<stdio.h>
#include<stdlib.h>
#include<conio.h> //getch()的头文件
#include<dos.h>
#include<string.h>
#include"stu.h"
#define LEN sizeof(struct student)
#define FORMAT "%-8d%-15s%-12.1lf%-12.1lf%-12.1lf%-12.1lf\n"
#define DATA stu[i].num,stu[i].name,stu[i].elec,stu[i].expe,stu[i].requ,stu[i].sum
/*
修改这个函数没用,修改之后只是名字改了,成绩没发生任何变化
*/
//菜单
void menu()
{
system("cls");
printf("\n\n\n\n");
printf("\t\t|--------------学生信息管理系统--------------|\n");
printf("\t\t| |\n");
printf("\t\t| 1.录入学生信息 |\n");
printf("\t\t| 2.查找学生信息 |\n");
printf("\t\t| 3.删除学生信息 |\n");
printf("\t\t| 4.修改学生信息 |\n");
printf("\t\t| 5.插入学生信息 |\n");
printf("\t\t| 6.排序 |\n");
printf("\t\t| 7.统计学生总数 |\n");
printf("\t\t| 8.显示所有学生信息 |\n");
printf("\t\t| 0.退出系统 |\n");
printf("\t\t| |\n");
printf("\t\t|--------------------------------------------|\n");
printf("\t\t\t\t请选择(0-8):");
}
//录入学生成绩信息
//每次录入会覆盖之前的信息
void in()
{
int i, m = 0; //m是记录的条数
char ch[2]; //命令选项:y/n
FILE* fp; //定义文件指针
//打开指定文件,a+:打开文件在文件尾部进行读写,文件不存在则创建同名的新文件
if ((fp = fopen("data.txt", "a+")) == NULL)
{
printf("文件不存在!\n");
return;
}
//是否达到文件尾部:feof=0到达了文件末尾,feof返回值非0,没有到达文件末尾
while (!feof(fp))
{
//从fp所指文件读取最多一个对象到数组stu中,对象的大小为LEN个字节,
//返回成功读取的对象个数
if (fread(&stu[m], LEN, 1, fp) == 1)
{
m++; //统计当前记录条数
}
}
fclose(fp);
if (m == 0)
{
printf("文件中没有记录!\n");
}
else
{
show(); //调用show函数,显示原有信息
}
//wb:以只写方式打开文件,向文件内写入数据,文件不存在创建同名的新文件
if ((fp = fopen("data.txt", "wb")) == NULL)
{
printf("文件不存在!\n");
return;
}
printf("输入学生信息(y/n):");
scanf("%s", ch);
//strcmp比较的两个字符串相等返回0
//判断是否要录入新信息
while (strcmp(ch, "Y") == 0 || strcmp(ch, "y") == 0)
{
printf("number:");
scanf("%d", &stu[m].num); //输入学生学号
//查找是否已经存在输入的学号
for (i = 0; i < m; i++)
{
if (stu[i].num == stu[m].num)
{
printf("number已经存在了,按任意键继续!\n");
getch();
fclose(fp);
return;
}
}
printf("name:");
scanf("%s", &stu[m].name); //输入学生姓名
printf("elective:");
scanf("%lf", &stu[m].elec); //输入选修课成绩
printf("experiment:");
scanf("%lf", &stu[m].expe); //输入实验课成绩
printf("required course:");
scanf("%lf", &stu[m].requ); //输入必修课成绩
stu[m].sum = stu[m].elec + stu[m].expe + stu[m].requ; //计算出总成绩
//将stu数组中的1个大小为LEN个字节的对象存入fp所指的文件中
//返回写入成功的条数
if (fwrite(&stu[m], LEN, 1, fp) != 1)
{
printf("不能保存!\n");
getch();
}
else
{
printf("%s的信息被保存!\n", stu[m].name);
m++; //当前记录条数+1
}
printf("继续(y/n):");
scanf("%s", ch);
}
fclose(fp);
printf("OK!\n");
}
//查找学生信息
void search()
{
FILE* fp;
int snum, i, m = 0;
//rb:只读,不能创建新文件
if ((fp = fopen("data.txt", "rb")) == NULL)
{
printf("文件不存在!\n");
return;
}
while (!feof(fp))
{
//从fp所指文件读取最多一个对象到数组stu中,对象的大小为LEN个字节,
//返回成功读取的对象个数
if (fread(&stu[m], LEN, 1, fp) == 1)
{
//每次读一个下标后移一位
m++;
}
}
fclose(fp);
if (m == 0)
{
printf("文件中没有记录!\n");
return;
}
printf("请输入number:");
scanf("%d", &snum);
for (i = 0; i < m; i++)
{
if (snum == stu[i].num) //查找输入的学号是否在记录中
{
printf("number name elective experiment required sum\t\n");
printf(FORMAT, DATA); //将查找出的结果按照指定格式输出
break;
}
}
if (i == m)
{
printf("没有找到这名学生的信息!\n"); //未找到要查找的信息
}
}
//删除学生信息
void del()
{
FILE* fp;
int snum, i, j, m = 0;
char ch[2]; //输入选择y/n
//r+:读写,文件不存在会出错
if ((fp = fopen("data.txt", "r+")) == NULL) //data.txt文件不存在
{
printf("文件不存在!\n");
return;
}
//没有到达文件尾部,每次就将1个大小为LEN的对象存入stu数组中
while (!feof(fp))
{
if (fread(&stu[m], LEN, 1, fp) == 1)
m++;
}
fclose(fp);
if (m == 0)
{
printf("文件中没有记录!\n"); //data.txt文件存在,但文件中没有内容
return;
}
printf("请输入学生的学号:");
scanf("%d", &snum);
for (i = 0; i < m; i++)
if (snum == stu[i].num)
{
printf("找到了这条记录,是否删除?(y/n):");
scanf("%s", ch);
if (strcmp(ch, "Y") == 0 || strcmp(ch, "y") == 0) //判断是否要进行删除
{
for (j = i; j < m; j++)
{
stu[j] = stu[j + 1]; //让后一条记录移动到前一个记录的位置,覆盖掉要删除的数据
}
m--; //记录的总条数减1
//wb:只写
if ((fp = fopen("data.txt", "wb")) == NULL)
{
printf("文件不存在!\n");
return;
}
//将更改后的记录写入指定的磁盘文件
for (j = 0; j < m; j++)
{
//保存失败
if (fwrite(&stu[j], LEN, 1, fp) != 1)
{
printf("Can't save!\n");
getch();
}
}
fclose(fp);
printf("删除成功!\n");
//删除成功后返回,退出函数
return;
}
else
{
printf("找到了记录,但不删除!\n");
//不删除返回,退出函数
return;
}
break;
}
printf("没有找到这名学生!\n"); //未找到要查找的信息
}
//修改学生信息
void modify()
{
FILE* fp;
//struct student t;
int i = 0, j = 0, m = 0, snum;
if ((fp = fopen("data.txt", "r+")) == NULL)
{
printf("文件不存在!\n");
return;
}
while (!feof(fp))
{
//将fp所指文件中的一个大小为LEN的对象存入stu数组中
if (fread(&stu[m], LEN, 1, fp) == 1)
m++;
}
if (m == 0)
{
printf("文件中没有记录!\n");
fclose(fp);
return;
}
show; //显示所有学生信息
printf("请输入要修改的学生的number:");
scanf("%d", &snum);
for (i = 0; i < m; i++)
{
//检查文件中是否有要修改的学生信息
if (snum == stu[i].num)
{
printf("找到了这名学生,可以修改他的信息!\n");
printf("name:");
scanf("%s", stu[i].name); //输入名字
printf("elective:");
scanf("%lf", &stu[i].elec); //输入选修课成绩
printf("experiment:");
scanf("%lf", &stu[i].expe); //输入实验课成绩
printf("required course:");
scanf("%lf", &stu[i].requ); //输入必修课成绩
printf("修改成功!\n");
stu[i].sum = stu[i].elec + stu[i].expe + stu[i].requ; //计算出总成绩
//wb:只写,文件不存在创建同名的新文件
if ((fp = fopen("data.txt", "wb")) == NULL)
{
printf("不能打开文件!\n");
return;
}
//将新修改的信息写入指定的磁盘文件中
for (j = 0; j < m; j++)
{
//将stu数组中的1个大小为LEN个字节的对象存入fp所指的文件
//返回保存成功的条数
if (fwrite(&stu[j], LEN, 1, fp) != 1)
{
printf("不能保存文件!\n");
getch();
}
}
fclose(fp);
break;
}
}
if (i == m)
printf("没有找到这名学生!\n"); //未找到要修改的学生的信息
}
//插入学生信息
void insert()
{
FILE* fp;
int i, j, k, m = 0, snum;
//打开一个文本文件进行读写,文件不存在会出错
if ((fp = fopen("data.txt", "r+")) == NULL)
{
printf("文件不存在!\n");
return;
}
//计算出文件中对象的个数
while (!feof(fp))
{
//从fp所指文件读取最多一个对象到数组stu中,对象的大小为LEN个字节,
//返回成功读取的对象个数
if (fread(&stu[m], LEN, 1, fp) == 1)
m++;
}
if (m == 0)
{
printf("文件中没有记录!\n");
fclose(fp);
return;
}
printf("请输入要插入的位置(location---要插入到哪个学生的学号后面):\n");
scanf("%d", &snum); //输入要插入的位置,要插入到哪个学生的学号后面
//找到对应学号的下标
for (i = 0; i < m; i++)
{
if (snum == stu[i].num)
break;
}
//从最后一条记录到要要插入的位置所有数据向后移动一位
for (j = m - 1; j>i; j--)
{
stu[j + 1] = stu[j];
}
printf("请输入要插入的学生信息!\n");
printf("number:");
scanf("%d", &stu[i + 1].num);
for (k = 0; k <= m; k++)
{
if (k == i + 1)
continue;
//m:未插入前数据的条数 stu[m].num:插入之后最后一条数据的学号
//如果前m项中有一项的学号和最后一位学号相同,就退出插入
if (stu[k].num == stu[i+1].num)
{
printf("number已经存在,按任意键继续!");
getch();
fclose(fp);
return;
}
}
printf("name:");
scanf("%s", stu[i+1].name); //输入名字
printf("elective:");
scanf("%lf", &stu[i+1].elec); //输入选修课成绩
printf("experiment:");
scanf("%lf", &stu[i+1].expe); //输入实验课成绩
printf("required course:");
scanf("%lf", &stu[i+1].requ); //输入必修课成绩
stu[i+1].sum = stu[i+1].elec + stu[i+1].expe + stu[i+1].requ; //计算出总成绩
printf("插入成功!按任意键返回主界面!\n");
//如果文件不存在,则给出提示,wb:只写,文件不存在则创建同名的新文件
if ((fp = fopen("data.txt", "wb")) == NULL)
{
printf("不能打开!\n");
return;
}
for (k = 0; k <= m; k++)
{
if (fwrite(&stu[k], LEN, 1, fp) != 1)
{
printf("不能保存!\n");
getch();
}
}
fclose(fp);
}
//排序
void order()
{
FILE* fp;
struct student t;
int i = 0, j = 0, m = 0;
//r+:读写,但文件不存在会出错
if ((fp = fopen("data.txt","r+")) == NULL)
{
printf("文件不存在!\n");
return;
}
while (!feof(fp))
{
//从fp所指文件中每次读取一个大小为LEN的对象存到数组stu中
if (fread(&stu[m], LEN, 1, fp) == 1)
{
m++;
}
}
fclose(fp);
if (m == 0)
{
printf("文件中没有记录!\n");
return;
}
//wb:只写,文件不存在则创建新文件
if ((fp = fopen("data.txt", "wb")) == NULL)
{
printf("文件不存在!\n");
return;
}
//双重for循环实现成绩比较交换
for (i = 0; i < m - 1; i++)
{
for (j = i + 1; j < m; j++)
{
if (stu[i].sum < stu[j].sum)
{
t = stu[i];
stu[i] = stu[j];
stu[j] = t;
}
}
}
//wb:只写,文件不存在则创建新文件
if ((fp = fopen("data.txt", "wb")) == NULL)
{
printf("文件不存在!\n");
return;
}
for (i = 0; i < m; i++)
{
//从stu数组中每次拿出一个大小为LEN的对象写入fp所指文件中
if (fwrite(&stu[i], LEN, 1, fp) != 1)
{
printf("不能保存文件!\n");
return;
}
}
fclose(fp);
printf("保存成功!\n");
}
//统计学生总数
void total()
{
FILE* fp;
int m = 0;
//r+:读写,但文件不存在会出错
if ((fp = fopen("data.txt", "r+")) == NULL)
{
printf("文件不存在!\n");
return;
}
while (!feof(fp))
{
//从fp所指文件中每次读取一个大小为LEN的对象存到数组stu中
if (fread(&stu[m], LEN, 1, fp) == 1)
{
m++;
}
}
if (m == 0)
{
printf("文件中无内容!\n");
fclose(fp);
return;
}
printf("这个班级共有%d名学生!\n", m);
fclose(fp);
}
//显示所有学生信息
void show()
{
FILE* fp;
int i, m = 0;
//只读:文件不存在就会出错
fp = fopen("data.txt", "rb");
//统计文件中对象的个数
while (!feof(fp))
{
//从fp所指文件中每次读取一个大小为LEN的对象存到数组stu中
if (fread(&stu[m], LEN, 1, fp) == 1)
{
m++;
}
}
fclose(fp);
printf("number name elective experiment required sum\t\n");
for (i = 0; i < m; i++)
{
printf(FORMAT, DATA); //将信息按指定格式打印
}
}
void main()
{
system("color f0\n"); //白底黑字
int n;
menu();
scanf("%d", &n); //输入选择功能的编号
while (n)
{
switch (n)
{
case 1:
in();
break;
case 2:
search();
break;
case 3:
del();
break;
case 4:
modify();
break;
case 5:
insert();
break;
case 6:
order();
break;
case 7:
total();
break;
case 8:
show();
break;
default:
break;
}
/*
getch()函数会读取一个输入的字符,但是并不会在屏幕上显示出,
在这里getch的作用是什么?
用getch(); 会等待你按下任意键,再继续执行下面的语句;
*/
getch();
menu(); //执行完功能后显示菜单界面
scanf("%d",&n);
}
}