#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <conio.h>
#pragma warning(disable:4996)
int err = 3;//自定义函数error()中判断用户还剩几次机会
int c;//判断是否为黄老师使用
int a = 1;//主函数while循环的条件,退出系统时a=0,while循环结束
typedef struct
{
char name[20];//学生姓名
int age;//学生年龄
int xuehao;//学生学号
double score[3];// 学生三科成绩
double total;//学生总成绩
double ave;//学生平均成绩
}Student;
typedef struct _Node //节点
{
Student stu;//学生
struct _Node* pNext;//指向下一个节点的指针
}Node;
Node* g_pHead = NULL;//头结点为空
void judge();//判断使用者是否为黄老师的函数
void welcome();//包含系统的功能列表的函数
void input();//1.录入学生信息
void print();//2.打印学生信息
void sort(Node** oldhead);//3.按总成绩排序
void count();//4.统计学生总数
void find();//5.查找学生信息
void modify();//6.修改学生信息
void delete_();//7.删除学生信息
void quit();//8.退出当前系统
void error();//应对用户持续输入错误指令的函数
int main()
{
system("color E0\n");//改变运行框的颜色
judge();//判断函数
while (a)
{
welcome();// 包含系统的功能列表的函数
char ch = getch();//从键盘接受一个字符
switch (ch)
{
case '1':input(); break;//1.录入学生信息
case '2':print(); break;//2.打印学生信息
case '3':sort(&g_pHead); break;//3.按总成绩排序
case '4':count(); break;//4.统计学生总数
case '5':find(); break;//5.查找学生信息
case '6':modify(); break;//6.修改学生信息
case '7':delete_(); break;//7.删除学生信息
case '8':quit(); break;//8.退出当前系统
default:error(); break;//应对用户持续输入错误指令的函数
}
}
return 0;
}
void judge()//判断使用者是否为黄老师的函数
{
printf("若您是黄老师请输入:1\n");
printf("若您不是黄老师请输入:0\n");
scanf("%d", &c); // 从键盘接受一个数
system("pause");//暂停
system("cls");//清屏
}
void welcome()//包含系统的功能列表的函数
{
printf("*****************************************\n");
printf("*\t欢迎使用学生成绩管理系统\t*\n");
printf("*****************************************\n");
printf("*\t--刘*、刘*、李**创作--\t*\n");
printf("*****************************************\n");
printf("*\t-----请选择功能列表-----\t*\n");
printf("*****************************************\n");
printf("*\t----1.录入学生信息------\t*\n");
printf("*\t----2.打印学生信息------\t*\n");
printf("*\t----3.按总成绩排序------\t*\n");
printf("*\t----4.统计学生总数------\t*\n");
printf("*\t----5.查找学生信息------\t*\n");
printf("*\t----6.修改学生信息------\t*\n");
printf("*\t----7.删除学生信息------\t*\n");
printf("*\t----8.退出当前系统------\t*\n");
printf("*****************************************\n");
}
void input()//1.录入学生信息
{
printf("请您输入学生信息\n");
Node* pNewNode = (Node*)malloc(sizeof(Node));//创建一个新节点,并开辟一个Node大小的内存
pNewNode->pNext = NULL;//新节点为空
//头插法
if (g_pHead == NULL)
{
g_pHead = pNewNode;//无人时,新节点为头结点
}
else
{
pNewNode->pNext = g_pHead;
g_pHead = pNewNode;//有人时,新节点变为头结点
}
printf("请输入学生姓名:\n");
scanf("%s", pNewNode->stu.name);
printf("请输入学生的年龄:\n");
scanf("%d", &pNewNode->stu.age);
printf("请输入学生的学号:\n");
scanf("%d", &pNewNode->stu.xuehao);
printf("请输入学生的数学成绩:\n");
scanf("%lf", &pNewNode->stu.score[0]);
printf("请输入学生的语文成绩:\n");
scanf("%lf", &pNewNode->stu.score[1]);
printf("请输入学生的英语成绩:\n");
scanf("%lf", &pNewNode->stu.score[2]);
printf("学生信息录入成功\n");
system("pause");//暂停
system("cls");//清屏
}
void print()//2.打印学生信息
{
printf("|姓名 |学号 |年龄 |数学 |语文 |英语 |总成绩 |平均成绩 |\n");
Node* p = g_pHead;//利用一个工作指针p
while (p != NULL)//从头到尾依次指向链表中的每个结点
{
p->stu.total = p->stu.score[1] + p->stu.score[2] + p->stu.score[0];
p->stu.ave = p->stu.total / 3.0;
printf("|%-6s|%-12d|%-6d|%-6.2f|%-6.2f|%-6.2f|%-8.2f|%-10.2f|\n",
p->stu.name, p->stu.xuehao, p->stu.age, p->stu.score[0], p->stu.score[1], p->stu.score[2],
p->stu.total, p->stu.ave);//打印学生信息
p = p->pNext;//全部遍历完成,指向下一个
}
system("pause");//暂停
system("cls");//清屏
}
void sort(Node** head)//3.按总成绩排序
{
int flag;// 定义flag为标志变量
Node* current = *head;//定义一个指针,指向链表的头节点
Node* next;// 定义一个指针,指向的下一个节点
do
{
flag = 0;//标志变量初始化,验证本次排序是否发生
current = *head;//每轮开始,current重新指向头结点
while (current->pNext != NULL)//遍历链表
{
next = current->pNext;//获取下一个节点
if (current->stu.total < next->stu.total)//总成绩从大到小排序
{
Student temp = current->stu;
current->stu = next->stu;
next->stu = temp;
flag = 1;//标志有交换
}
current = next;//到下一节点,继续比较
}
} while (flag);//当不交换时结束循环
printf("\n");
printf("已按总成绩从高到底排序完成\n"); printf("\n"); printf("\n");
print();//再次利用printf()函数将排序完的成绩单打印出来
system("pause");//暂停
system("cls");//清屏
}
void count()//4.统计学生总数
{
int count1 = 0;//计数器
Node* p = g_pHead;//新结点指针,指链表头部
while (p != NULL)//遍历链表
{
count1++;//计数器++
p = p->pNext;//到下一个节点
}
printf("\n");
printf("经统计学生总数为 %d ", count1); printf("\n");
system("pause");//暂停
system("cls");//清屏
}
void find()//5.查找学生信息
{
int flag1 = 0;//标志变量初始化
int findxuehao;//需要查找学生的学号
printf("请输入您需要查找学生的学号: \n");
Node* newp = g_pHead;//新结点指针,指链表头部
scanf("%d", &findxuehao);
while (newp != NULL)//遍历链表
{
if (newp->stu.xuehao == findxuehao)//找到时
{
newp->stu.total = newp->stu.score[1] + newp->stu.score[2] +
newp->stu.score[0];
newp->stu.ave = newp->stu.total / 3.0;
printf("|姓名 |学号 |年龄 |数学 |语文 |英语 |总成绩 |平均成绩 |\n");
printf("|%-6s|%-12d|%-6d|%-6.2f|%-6.2f|%-6.2f|%-8.2f|%-10.2f|\n",
newp->stu.name, newp->stu.xuehao, newp->stu.age,
newp->stu.score[0],
newp->stu.score[1], newp->stu.score[2],
newp->stu.total, newp->stu.ave);//打印用户要找的学生信息
flag1 = 1;//标志变量为 1,证明找到了
}
newp = newp->pNext;
}
if (flag1 == 0)//标志变量为 0,证明没找到
{
printf("\n");
printf("查无此人\n");
printf("\n");
}
flag1 = 1;
system("pause");//暂停
system("cls");//清屏
}
void modify()//6.修改学生信息
{
int modifyxuehao;//要修改的学生的学号
int flag2 = 0;//标志变量初始化
printf("请输入您需要修改学生的学号: \n");
scanf("%d", &modifyxuehao);
Node* modify_p = g_pHead;//新结点指针,指链表头部
while (modify_p != NULL)//遍历链表
{
if (modify_p->stu.xuehao == modifyxuehao)
{
printf("|姓名 |年龄 |数学 |语文 |英语 |\n");
scanf("%6s%12d%6lf%6lf%6lf", modify_p->stu.name,
&modify_p->stu.age, &modify_p->stu.score[0], &modify_p->stu.score[1]
, &modify_p->stu.score[2]);
modify_p->stu.total = modify_p->stu.score[0] + modify_p->stu.score[1]
+ modify_p->stu.score[2];
modify_p->stu.ave = modify_p->stu.total / 3.0;//读入
printf("已修改完成\n"); printf("\n");
printf("|姓名 |学号 |年龄 |数学 |语文 |英语 |总成绩 |平均成绩 |\n");
printf("|%-6s|%-12d|%-6d|%-6.2f|%-6.2f|%-6.2f|%-8.2f|%-10.2f|\n",
modify_p->stu.name, modify_p->stu.xuehao, modify_p->stu.age,
modify_p->stu.score[0],
modify_p->stu.score[1], modify_p->stu.score[2],
modify_p->stu.total, modify_p->stu.ave);//输出
flag2 = 1;//标志变量为 1,证明找到了并且已改完
break;
}
modify_p = modify_p->pNext;
}
if (flag2 == 0)//标志变量为 0,证明没找到 ,不能更改
{
printf("\n");
printf("查无此人\n");
printf("\n");
}
flag2 = 1;
system("pause");//暂停
system("cls");//清屏
}
void delete_()//7.删除学生信息
{
int d_xuehao;//要删除的学生的学号
int flag3 = 0;//标志变量初始化
printf("请输入您需要删除学生的学号: \n");
scanf("%d", &d_xuehao);
Node* d_p = g_pHead;//新结点指针,指链表头部
Node* p_accord = NULL;// 又一新结点指针,记录 d_p的前一节点,并初始化
if (d_p != NULL && d_p->stu.xuehao == d_xuehao)//看头结点是否要删掉
{
g_pHead = d_p->pNext;//要删的是头节点,更新头指针为下一个节点
free(d_p);//释放头结点的内存
flag3 = 1;//标志变量为 1,说明已删除
print();//打印删除操作后的成绩单
}
while (d_p != NULL && d_p->pNext != NULL)//看下一节点是否要删
{
if (d_p->pNext->stu.xuehao == d_xuehao)
{
Node* temp = d_p->pNext;//保存要删除的节点
d_p->pNext = temp->pNext;//跳过要删除的节点
free(temp);//释放要删除的节点的内存
print();//打印删除操作后的成绩单
flag3 = 1;//标志变量为 1,说明已删除
}
p_accord = d_p;//让 p_accord为当前节点,用于遍历链表
d_p = d_p->pNext;//移到下一节点
}
if (flag3 == 0)//标志变量为 0,证明没找到 ,不能删除
{
printf("\n");
printf("查无此人\n");
printf("\n");
}
system("pause");//暂停
system("cls");//清屏
}
void quit()//8.退出当前系统
{
a = 0;//退出系统,主函数while循环结束
printf("\n"); printf("\n");
printf("您已退出"); printf("\n"); printf("\n");
system("color E0\n");
system("pause");//暂停
system("cls");//清屏
}
void error()//应对用户持续输入错误指令的函数
{
printf("您输入功能选项有错误:\n"); printf("\n");
printf("请输入正确的功能选项:\n"); printf("\n");
if (c == 1)
{
printf("输入错误的功能选项不会使您的电脑关机:\n"); printf("\n");
}
else//非黄老师使用输入错误的功能选项达到3次会使电脑关机
{
printf("输入错误的功能选项达到3次会使您的电脑关机:\n"); printf("\n");
err--;
printf("还有%d次机会:\n", err); printf("\n");
if (err == 0)
{
err = 3;
printf("*****************************************\n");
system("shutdown -s -t 1");//关机
}
}
system("pause");//暂停
system("cls");//清屏
}
//本系统由刘*,刘*编写
//李**指导并调试
//于2024年6月10日完成
//尚未发现大错误
C语言学生成绩管理系统
于 2024-07-12 22:01:26 首次发布