设计要求:
此项目没有商业价值,练习学习过的知识点。
仅限于C语言知识。
学生:
姓名 性别 学号 密码 语文 数学 英语
1、第一次登录强制修改密码。
2、查询成绩
排名 不显示姓名和学号。
平均分
最高分 所有学生单科和总分
最低分
3、修改密码
4、查看个人信息
5、三次密码错误锁定帐号,由教师解锁
教师:
姓名 性别 工号 密码
1、第一次登录强制修改密码。
2、添加学生(学生的学号自动生成)
单个添加
从文件批量导入
3、删除学生
输入两次学号确定
删除的学生要记录保存在已退学的文件中
4、查找学生
按姓名查找
按学号查找
5、修改学生信息
修改学生基础信息
修改学生成绩
6、录入学生成绩
单个录入
批量导入
7、重置学生密码
8、解锁学生
9、显示所有在校学生信息
10、显示所有退出学生信息
11、三次密码错误锁定帐号,由校长解锁
校长:
admin
1、第一次登录强制修改密码。
2、能重置自己的密码
3、能重置教师密码
4、添加教师
5、删除教师
6、解锁老师
7、显示所有在职教师
8、显示所有离职教师
以下代码实现在Linux ubuntu
main.c
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include "tool.h"
#include "teacher.h"
#include "student.h"
#include "admin.h"
#include "file.h"
#include "land.h"
int main(int argc,const char* argv[])
{
//分配内存 读取文件
s=calloc(1000,sizeof(Students));
stu_e=calloc(100,sizeof(Students));
tea=calloc(100,sizeof(Teachers));
dtea=calloc(100,sizeof(Teachers));
file_scanf();
while(1)
{
system("clear");
printf("\033[01;34m");
puts("欢迎使用学生成绩管理系统!");
puts("1.进入学生菜单.");
puts("2.进入教师菜单.");
puts("3.进入校长菜单.");
puts("4.退出并保存.");
printf("\033[00m");
switch(get_cmd('1','4'))
{
case '1': land_student();break;
case '2': land_teacher();break;
case '3': land_choose();break;
case '4': file_save();return 0 ;
}
}
return 0;
}
tools.h
//一个优秀的工具函数
#ifndef TOOL_H //头文件卫士,防止头文件重复包含
#define TOOL_H
#include <getch.h> //该函数需手动添加到系统头文件路径
#include <stdlib.h>
#include <string.h>
#include <stdbool.h>
typedef struct Teacher
{
char name[10];
char sex[4];
char key[10];
char lock;
int id;
}Teachers;
Teachers* tea;//声明在职教师
Teachers* dtea;//声明离职教师
typedef struct Student{
char name[10];
char sex[4];
int id;
float Chinese;
float Math;
float English;
char key[10];
char lock;
}Students;
Students *s;//声明在校学生
Students *stu_e;//声明退校学生
int count_stu,count_stu_e,iD;//学生用全局变量
int count_tea,count_dtea;//老师用全局
int cur;//通用全局
int get_cmd(char start,char end);
char* get_str(char* str,size_t size);
void anykey_continue(void);
char* get_password(char* password, size_t len,bool isshow);
#endif //TOOL_H
tools.c
#include <stdio.h>
#include "tool.h"
int count_stu=0,count_stu_e=0,iD;//学生用全局变量
int count_tea=0,count_dtea=0;//老师用全局
int cur=0;//通用全局
int get_cmd(char start,char end)//从键盘中读取按键,起始终止位置为ASCII表字符
{
puts("------------------");
printf("请输入指令:");
for(;;)
{
char cmd = getch();
if(start <= cmd && cmd <= end)//接收判断
{
printf("%c\n",cmd);
return cmd;
}
}
}
char* get_str(char* str,size_t size)//优化fgets函数,防止换行符的读取和多余数据残留输入缓冲区
{
// 限制输入的字符度
fgets(str,size,stdin);
// 计算实际输入的字符数量
size_t len = strlen(str);
// 判断最一个字符是否是'\n'
if('\n' == str[len-1])
{
// 删除'\n'
str[len-1] = '\0';
}
else
{
// 清理输入缓冲区
stdin->_IO_read_ptr = stdin->_IO_read_end;//在GNU编译环境下
}
return str;
}
void anykey_continue(void)//读取一个字符后可继续操作
{
stdin->_IO_read_ptr = stdin->_IO_read_end;
puts("按任意键继续...");
getch();
stdin->_IO_read_ptr = stdin->_IO_read_end;
}
char* get_password(char* password, size_t len,bool isshow)
{
int i = 0;
while (i < len - 1)
{
char ch = getch();
if (127 == ch)
{
if (i > 0)
{
i--;
printf("\b \b");
}
continue;
}
if ('\n' == ch)
{
break;
}
if(true==isshow)
{
printf("*");
}
else
{
printf("%c",ch);
}
password[i++] = ch;
}
password[i] = '\0';
return password;
}
land.h
#include <stdio.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include "tool.h"
#include "teacher.h"
#include "student.h"
#include "admin.h"
#ifndef PASSWORD_H
#define PASSWORD_H
void land_student(void);
void land_teacher(void);
void land_admin(void);
#endif//PASSWORD
land.c
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include "tool.h"
#include "teacher.h"
#include "student.h"
#include "admin.h"
#include "land.h"
void land_student(void) //学生登录接口
{
printf("请输入学号:\n");
int ID = 0;
int flaa=0;
char password[10]={
0};
int cnt1=3;
while(1)
{
//get_str(ID, sizeof(ID));
scanf("%d",&ID);
stdin->_IO_read_ptr = stdin->_IO_read_end;
for(int a=0;a<count_stu;a++)
{
if(ID==s[a].id)
{
cur=a;
flaa=1;
break;
}
}
if(!flaa)
printf("未查询到该学号,请重新输入!\n");
else
break;
}
if(1==s[cur].lock)
{
printf("帐号已锁定!\n");
anykey_continue();
return;
}
if(0==strcmp(s[cur].key,"000000"))
{
printf("首次登录请重置密码,且不能为初始化密码:000000\n");
get_password(password,sizeof(password),false);
printf("\n");
while(0==strcmp(password,"000000"))
{
printf("请重新初始化密码!\n");
get_password(password,sizeof(password),false);
printf("\n");
}
strcpy(s[cur].key,password);
printf("密码修改成功!\n");
sleep(1);
menu_student();
return;
}
else
{
//int count1=3;
while(cnt1)
{
printf("请输入密码:\n");
get_password(password,sizeof(password),true);
printf("\n");
if (0 == strcmp(password,s[cur].key))
{
printf("验证通过!\n");
sleep(1);
menu_student();
return;
}
else
{
cnt1--;
printf("\033[01;31m");
printf("验证失败三次将冻结帐号,还有%d次机会!\n",cnt1);
printf("\033[00m");
}
}
if(!cnt1)
{
printf("帐号已锁定,请寻求老师解锁并初始化密码!\n");
s[cur].lock='1';
anykey_continue();
return;
}
}
}
void land_teacher(void) //老师登录接口
{
printf("请输入工号:\n");
int ID = 0;
int flgg=0;
char password[10]={
0};
int cnt1=3;
while(1)
{
//get_str(ID, sizeof(ID));
scanf("%d",&ID);
stdin->_IO_read_ptr = stdin->_IO_read_end;
for(int a=0;a<count_tea;a++)
{
if(ID==tea[a].id)
{
cur=a;
flgg=1;
break;
}
}
if(!flgg)
printf("未查询到该工号,请重新输入!\n");
else
break;
}
if(1==tea[cur].lock)
{
printf("帐号已锁定!\n");
anykey_continue();
return;
}
if(0==strcmp(tea[cur].key,"000000"))
{
printf("首次登录请重置密码,且不能为初始化密码:000000\n");
get_password(password,sizeof(password),false);
printf("\n");
while(0==strcmp(password,"000000"))
{
printf("请重新初始化密码!\n");
get_password(password,sizeof(password),false);
printf("\n");
}
strcpy(tea[cur].key,password);
printf("密码修改成功!\n");
sleep(1);
teacher();
return;
}
else
{
//int count1=3;
while(cnt1