C语言课程设计--学生成绩管理系统

要求:

(1) 学生成绩信息保存在文件中

(2) 学生成绩信息查询、删除、修改和显示

(3) 学生成绩总分计算和排名

(4) 学生成绩信息的统计:根据科目统计每个分数段的人,统计结果可以保存文件中。

(5) 利用菜单管理

目录

(1) func.h

(2) func.cpp

(3) main.cpp

 

#ifndef _FUNC_H
#define _FUNC_H
#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
#include <malloc.h>
#include <string.h>
#define LEN sizeof(struct Student)

struct Score
{
	float gaoshu;
	float yingyu;
	float yuwen;
};

struct Student
{
	char name[20];
	int id;
	struct Score score;
	float sum;
	int rank;
	struct Student *next;
};

void login();
int menu();

void createList();

void ranksum();

void writeInFile();

void showOriginalInfo();

void showOneStudentInfo(struct Student *p);

void insertInfo();

void queryInfo();

void modifyInfo();

int modifyMenu();

int idOrName();

void showData();

#endif

 

#include "func.h"

char title[7][20] = { "学号\t", "姓名\t", "高数\t", "语文\t", "英语\t", "总分\t", "排名" };

struct Student *head;

void login()
{
	printf("\n\n\t\t\t----------------- 学生信息管理系统 -----------------\n");
	printf("\n\n\t\t\t                    版本号:v1.0                     \n");
	printf("\n\n\t\t\t                      By Zyf                        \n");
}

int menu()
{
	int input;

	do
	{
		system("cls");
		printf("\n\n");
		printf("\t\t\t _________________________________________________\n");
		printf("\t\t\t|                                                 |\n");
		printf("\t\t\t|            *****学生信息管理系统*****           |\n");
		printf("\t\t\t|_________________________________________________|\n");
		printf("\t\t\t|                                                 |\n");
		printf("\t\t\t|可选项 :                                        |\n");
		printf("\t\t\t|            1.显示学生信息                       |\n");
		printf("\t\t\t|            2.查询学生信息                       |\n");
		printf("\t\t\t|            3.修改学生信息                       |\n");
		printf("\t\t\t|            4.删除学生信息                       |\n");
		printf("\t\t\t|            5.各科成绩各分数段人数表             |\n");
		printf("\t\t\t|            0.退出管理系统                       |\n");
		printf("\t\t\t|_________________________________________________|\n");
		printf("请选择:");
		scanf("%d", &input);
		if (input < 0 || input > 5)
		{
			printf("输入有误");
			Sleep(1000);
			fflush(stdin);	//防止输入符号时造成多次循环
		}
	} while (input < 0 || input > 5);

	return input;
}

int modifyMenu()
{
	int input;

	do
	{
		printf("\t可选项 :\n");
		printf("\t\t1.姓名\n");
		printf("\t\t2.高数\n");
		printf("\t\t3.英语\n");
		printf("\t\t4.语文\n");
		printf("\t\t0.退出\n");
		printf("请选择:");
		scanf("%d", &input);
		if (input < 0 || input > 4)
		{
			printf("输入有误\n");
			Sleep(1000);
			fflush(stdin);	//防止输入符号时造成多次循环
		}
	} while (input < 0 || input > 4);

	return input;
}

int idOrName()
{
	int input;

	do
	{
		printf("\t可选项 :\n");
		printf("\t\t1.学号\n");
		printf("\t\t2.姓名\n");
		printf("\t\t0.退出\n");
		printf("请选择:");
		scanf("%d", &input);
		if (input < 0 || input > 2)
		{
			printf("输入有误\n");
			Sleep(1000);
			fflush(stdin);	//防止输入符号时造成多次循环
		}
	} while (input < 0 || input > 2);

	return input;
}

void ranksum()	//每进行一次数据修改都重新总分, 排名
{
	struct Student *p, *temp;
	int i = 1, j;
	temp = head;
	temp->rank = 1;
	p = head->next;
	while (p != NULL)		//擂台法计算排名
	{
		temp = head;
		p->rank = 1;
		for (j = 0; j < i; j++)
		{
			if (p->sum > temp->sum)
			{
				temp->rank = temp->rank + 1;
			}
			else if (p->sum < temp->sum)
			{
				p->rank = p->rank + 1;
			}
			temp = temp->next;
		}
		p = p->next;
		i++;
	}
}

void createList()	//初始化链表
{
	int i = 1, j;
	FILE *fp;

	struct Student *p, *q, *temp;

	p = (struct Student *)malloc(LEN);

	if ((fp = fopen("./database.txt", "r")) == NULL)
	{
		printf("open error on reading");
		exit(0);
	}
	//从源文件中读取信息
	fscanf(fp, "%d%s%f%f%f", &p->id, p->name, &p->score.gaoshu, &p->score.yingyu, &p->score.yuwen);	
	p->sum = p->score.gaoshu + p->score.yingyu + p->score.yuwen;
	p->rank = 1;
	head = p;

	while (!feof(fp))
	{
		q = (struct Student *)malloc(LEN);
		fscanf(fp, "%d%s%f%f%f", &q->id, q->name, &q->score.gaoshu, &q->score.yingyu, &q->score.yuwen);
		q->sum = q->score.gaoshu + q->score.yingyu + q->score.yuwen;
		q->rank = 1;
		p->next = q;
		p = q;

		temp = head;	//每一次排名都从第一个节点开始比较

		for (j = 0; j < i; j++)
		{
			if (p->sum > temp->sum)
			{
				temp->rank = temp->rank + 1;
			}
			else if (p->sum < temp->sum)
			{
				p->rank = p->rank + 1;
			}
			temp = temp->next;
		}
		i++;
	}
	p->next = NULL;

	fclose(fp);
}

void writeInFile()	
{
	FILE *fp;
	struct Student *p;

	p = head;

	if ((fp = fopen("./data.txt", "w")) == NULL)
	{
		printf("open error on writing");
		exit(0);
	}
	while (p)
	{
		fprintf(fp, "%d\t%s\t%.2f\t%.2f\t%.2f\t%.2f\t  %d\n", p->id, p->name, p->score.gaoshu, p->score.yingyu, p->score.yuwen, p->sum, p->rank);
		p = p->next;
	}
	printf("Successfully writing.\n");
	fclose(fp);
}

void showOriginalInfo()
{
	int i, count = 0;
	struct Student *p;
	p = head;
	printf("学生成绩一览表:\n");
	printf("\t -------------------------------------------------------\n\t|");
	for (i = 0; i < 7; i++)
	{
		printf("%2s ", title[i]);
	}

	printf("  |\n");
	while (p)
	{
		printf("\t|%d\t %s\t%.2f\t%.2f\t%.2f\t%.2f\t  %d\t|\n", p->id, p->name, p->score.gaoshu, p->score.yingyu, p->score.yuwen, p->sum, p->rank);
		p = p->next;
		count++;
	}
	printf("\t -------------------------------------------------------\n\n");
	printf("总人数: %d\n\n", count);
}

void showOneStudentInfo(struct Student *p)	//每查询一个学生都输出其个人信息
{
	int i;
	printf("------------------------\n");
	printf("\t");
	for (i = 0; i < 7; i++)
	{
		printf("%2s ", title[i]);
	}
	printf("\n\t");
	printf(" %d\t %s\t%.2f\t%.2f\t%.2f\t%.2f\t  %d\n", p->id, p->name, p->score.gaoshu, p->score.yingyu, p->score.yuwen, p->sum, p->rank);
	printf("------------------------\n");
}

void queryInfo()
{
	struct Student *p;
	int flag, i, input, id;
	char name[50], ch;
	while (1)
	{
		p = head;
		flag = 0;
		
		input = idOrName();
		switch (input)
		{
		case 1:
			printf("\n\t输入查询学生学号:");
			scanf("%d", &id);
			getchar();
			Sleep(500);
			while (p)
			{
				if (p->id == id)
				{
					flag = 1;
					break;		//查到信息,退出while
				}
				p = p->next;
			}
			break;
		case 2:
			printf("\n\t输入查询学生姓名:");
			scanf("%s", name);
			getchar();
			Sleep(500);
			while (p)
			{
				if (strcmp(p->name, name) == 0)
				{
					flag = 1;
					break;		//查到信息,退出while
				}
				p = p->next;
			}
			break;
		case 0:
			Sleep(500);
			return;
		default:
			break;
		}
		
		if (flag == 1)		//找到了
		{
			showOneStudentInfo(p);	//显示该学生信息
			printf("是否继续查询(y/n):");
			while (1)
			{
				scanf("%c", &ch);
				fflush(stdin);	//清空缓冲区,防止输入多字符
				if (ch == 'n' || ch == 'N')
				{
					return;
				}
				else if (ch == 'y' || ch == 'Y')
				{
					break;
				}
				else
				{
					printf("错误指令!请重新输入(y/n):");
				}
			}
		}
		if (flag == 0)
		{
			printf("未找到该学生记录,是否重新输入(y/n):");
			while (1)
			{
				scanf("%c", &ch);
				fflush(stdin);
				if (ch == 'n' || ch == 'N')
				{
					return;
				}
				else if (ch == 'y' || ch == 'Y')
				{
					break;
				}
				else
				{
					printf("错误指令!请重新输入(y/n):");
				}
			}
		}
	}
}

void modifyInfo()
{
	struct Student *p;
	p = head;
	int flag = 0, i, input, id;
	char name[50], ch;
	char newName[50];
	float newGaoShu, newYingyu, newYuwen;

	while (1)
	{
		p = head;
		flag = 0;
		input = idOrName();
		switch (input)
		{
		case 1:
			printf("\n\t输入查询学生学号:");
			scanf("%d", &id);
			getchar();
			Sleep(500);
			while (p)
			{
				if (p->id == id)
				{
					flag = 1;
					break;		//查到信息,退出while
				}
				p = p->next;
			}
			break;
		case 2:
			printf("\n\t输入查询学生姓名:");
			scanf("%s", name);
			getchar();
			Sleep(500);
			while (p)
			{
				if (strcmp(p->name, name) == 0)
				{
					flag = 1;
					break;		//查到信息,退出while
				}
				p = p->next;
			}
			break;
		case 0:
			Sleep(500);
			return;
		default:
			break;
		}

		if (flag == 1)
		{
			showOneStudentInfo(p);	//找到了,显示该学生信息

			while (1)
			{
				input = modifyMenu();
				switch (input)
				{
				case 1:
					printf("请输入姓名:");
					scanf("%s", newName);
					strcpy(p->name, newName);
					Sleep(500);
					printf("-----------修改成功,继续修改或退出-----------\n------------------------\n");
					break;
				case 2:
					printf("请输入高数成绩:");
					scanf("%f", &newGaoShu);
					p->score.gaoshu = newGaoShu;
					Sleep(500);
					printf("-----------修改成功,继续修改或退出-----------\n------------------------\n");
					break;

				case 3:
					printf("请输入英语成绩:");
					scanf("%f", &newYingyu);
					p->score.yingyu = newYingyu;
					Sleep(500);
					printf("-----------修改成功,继续修改或退出-----------\n------------------------\n");
					break;

				case 4:
					printf("请输入语文成绩:");
					scanf("%f", &newYuwen);
					p->score.yuwen = newYuwen;
					Sleep(500);
					printf("-----------修改成功,继续修改或退出-----------\n------------------------\n");
					break;
				case 0:
					Sleep(500);
					break;
				default:
					break;
				}
				if (input == 0)
				{
					p->sum = p->score.gaoshu + p->score.yingyu + p->score.yuwen;
					ranksum();
					writeInFile();	//重新排序并写入文件
					break;
				}
			}
			getchar();
			printf("是否继续修改(y/n):");
			while (1)
			{
				scanf("%c", &ch);
				fflush(stdin);	//清空缓冲区,防止输入多字符
				if (ch == 'n' || ch == 'N')
				{
					return;
				}
				else if (ch == 'y' || ch == 'Y')
				{
					break;
				}
				else
				{
					printf("错误指令!请重新输入(y/n):");
				}
			}
		}
		if (flag == 0)
		{
			printf("未找到该学生记录,是否重新输入(y/n):");
			while (1)
			{
				scanf("%c", &ch);
				fflush(stdin);
				if (ch == 'n' || ch == 'N')
				{
					return;
				}
				else if (ch == 'y' || ch == 'Y')
				{
					break;
				}
				else
				{
					printf("错误指令!请重新输入(y/n):");
				}
			}
		}
	}

}

void deleteInfo()
{
	struct Student *r, *p;
	int flag, i, input, id;
	char name[50], ch;

	while (1)
	{
		p = head;
		r = p;
		flag = 0;

		input = idOrName();
		switch (input)
		{
		case 1:
			printf("\n\t输入查询学生学号:");
			scanf("%d", &id);
			getchar();
			Sleep(500);
			while (p)
			{
				if (p->id == id)
				{
					flag = 1;
					break;		//查到信息,退出while
				}
				r = p;	//r记录该节点的前一个节点
				p = p->next;
			}
			break;
		case 2:
			printf("\n\t输入查询学生姓名:");
			scanf("%s", name);
			getchar();
			Sleep(500);
			while (p)
			{
				if (strcmp(p->name, name) == 0)
				{
					flag = 1;
					break;		//查到信息,退出while
				}
				r = p;
				p = p->next;
			}
			break;
		case 0:
			Sleep(500);
			return;
		default:
			break;
		}
		
		if (flag == 1)
		{
			showOneStudentInfo(p);

			printf("是否确定删除?(y/n)");
			scanf("%c", &ch);
			fflush(stdin);	//清空缓冲区,防止输入多字符
			if (ch == 'n' || ch == 'N')
			{
				break;
			}
			else if (ch == 'y' || ch == 'Y')
			{
				if (p == head)
				{
					head = head->next;	//头节点则直接删除
				}
				else
				{
					r->next = p->next;	//该节点的前一个节点指向下一个节点
				}
				ranksum();
				writeInFile();	//重新排序并写入文件
				printf("删除成功!\n");
			}
			else
			{
				printf("错误指令!请重新输入(y/n):");
			}
		}

		if (flag == 0)
		{
			printf("未找到该学生记录,是否重新输入(y/n):");
			while (1)
			{
				scanf("%c", &ch);
				fflush(stdin);
				if (ch == 'n' || ch == 'N')
				{
					return;
				}
				else if (ch == 'y' || ch == 'Y')
				{
					break;
				}
				else
				{
					printf("错误指令!请重新输入(y/n):");
				}
			}
		}

		printf("是否继续删除(y/n):");
		while (1)
		{
			scanf("%c", &ch);
			fflush(stdin);	//清空缓冲区,防止输入多字符
			if (ch == 'n' || ch == 'N')
			{
				return;
			}
			else if (ch == 'y' || ch == 'Y')
			{
				break;
			}
			else
			{
				printf("错误指令!请重新输入(y/n):");
			}
		}


	}
}

void showData()
{
	struct Student *p;
	int i;
	FILE *fp;
	char str[6][30] = { "0 - 60", "60 - 70", "70 - 80", "80 - 90", "90 - 100", "总人数" };
	p = head;

	int people[3][6] = { 0 };	//横列人数
	int allpeople[5] = { 0 };	//纵列相加的人数
	float score[3] = { 0.0 };
	//计算分数段人数
	while (p)
	{
		score[0] = p->score.gaoshu;
		score[1] = p->score.yingyu;
		score[2] = p->score.yuwen;
		
		for (i = 0; i < 3; i++)
		{
			if ((score[i] >= 0) && (score[i] <= 60))
			{
				people[i][0] += 1;
			}
			else if ((score[i] > 60) && (score[i] <= 70))
			{
				people[i][1] += 1;
			}
			else if ((score[i] > 70) && (score[i] <= 80))
			{
				people[i][2] += 1;
			}
			else if ((score[i] > 80) && (score[i] <= 90))
			{
				people[i][3] += 1;
			}
			else if ((score[i] > 90) && (score[i] <= 100))
			{
				people[i][4] += 1;
			}
			people[i][5] = people[i][0] + people[i][1] + people[i][2] + people[i][3] + people[i][4];
		}
		
		p = p->next;
	}

	for (i = 0; i < 5; i++)
	{
		allpeople[i] = people[0][i] + people[1][i] + people[2][i];
	}

	//显示信息
	printf("\n各科分数分段表:");
	printf("\n\n------------------------\n\t   ");
	for (i = 0; i < 6; i++)
	{
		printf("%s   ", str[i]);
	}
	printf("\n\n高数");
	for (i = 0; i < 6; i++)
	{
		printf("        %2d", people[0][i]);
	}
	printf("\n\n英语");
	for (i = 0; i < 6; i++)
	{
		printf("        %2d", people[1][i]);
	}
	printf("\n\n语文");
	for (i = 0; i < 6; i++)
	{
		printf("        %2d", people[2][i]);
	}
	printf("\n\n总人数");
	for (i = 0; i < 5; i++)
	{
		printf("      %2d  ", allpeople[i]);
	}
	printf("\n\n------------------------\n\n");

	//写入文件
	if ((fp = fopen("./people_info.txt", "w")) == NULL)
	{
		printf("open error on writing");
		exit(0);
	}
	
	fputs("\n各科分数分段表:\n\n------------------------\n        ", fp);
	for (i = 0; i < 6; i++)
	{
		fputs("    ", fp);
		fputs(str[i], fp);	
	}
	fputs("\n\n高数", fp);
	fprintf(fp, "        %3d        %3d        %3d        %3d        %3d        %3d\n", people[0][0], people[0][1], people[0][2], people[0][3], people[0][4], people[0][5]);

	fputs("\n\n英语", fp);
	fprintf(fp, "        %3d        %3d        %3d        %3d        %3d        %3d\n", people[1][0], people[1][1], people[1][2], people[1][3], people[1][4], people[1][5]);

	fputs("\n\n语文", fp);
	fprintf(fp, "        %3d        %3d        %3d        %3d        %3d        %3d\n", people[2][0], people[2][1], people[2][2], people[2][3], people[2][4], people[2][5]);

	fputs("\n\n总人数", fp);
	fprintf(fp, "      %3d        %3d        %3d        %3d        %3d\n", allpeople[0], allpeople[1], allpeople[2], allpeople[3], allpeople[4]);

	fputs("\n\n------------------------\n\n", fp);
	fclose(fp);
}

 

#include "func.h"

int main()
{
	login();
	Sleep(1500);
	createList();	//初始化链表信息
	writeInFile();	//将处理后的信息写入目标文件
	while (1)
	{
		switch (menu())
		{
		case 1:
			system("cls");
			printf("\n显示学生信息,内部逻辑处理中......\n\n");
			Sleep(500);
			system("cls");
			showOriginalInfo();
			break;

		case 2:
			system("cls");
			printf("\n查询学生信息,内部逻辑处理中......\n\n");
			Sleep(500);
			system("cls");
			queryInfo();
			break;

		case 3:
			system("cls");
			printf("\n修改学生信息,内部逻辑处理中......\n\n");
			Sleep(500);
			system("cls");
			modifyInfo();
			break;

		case 4:
			system("cls");
			printf("\n删除学生信息,内部逻辑处理中......\n\n");
			Sleep(500);
			system("cls");
			deleteInfo();
			break;

		case 5:
			system("cls");
			printf("\n各科成绩各分数段人数表,内部逻辑处理中......\n\n");
			Sleep(500);
			system("cls");
			showData();
			break;

		case 0:
			system("cls");
			printf("\n\n\t\t\t-------------------感谢使用!-------------------\n\n\n");
			Sleep(500);
			exit(-1);
			break;
		default:
			break;
		}
		system("PAUSE");
	}

	return 0;
}

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值