栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > C/C++/C#

学生成绩管理系统(C语言)

C/C++/C# 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

学生成绩管理系统(C语言)

学生成绩管理系统功能
  1. 菜单
  2. 查询学生信息
  3. 修改学生信息
  4. 删除学生信息
  5. 显示学生信息
  6. 各科成绩各分数段人数统计
  7. 退出系统
  8. 异常输入报错
学生成绩管理系统代码(含注释)

Function.h文件代码:

#ifndef _CHANGEINFOR_H
#define _CHANGEINFOR_H

#include 
#include 
#include
#define ClassNum 3

//结构体
struct Student
{
	int id;
	char name[10];
	float Class[ClassNum];//三门科目
	float total;
	int Rank;
	struct Student *next;
};

//函数声明
void ChangeInfor(struct Student *h,char *title);
int ClassfyGrade(struct Student *h);
struct Student *create();
struct Student *InforDelete(struct Student *h,char *title );
int openfile(struct Student *h );
void ReCalculate(struct Student *h);
void ReRank(struct Student *h);
int SaveNew(struct Student *h , char *s);
void SearchStu(struct Student *h,char *title);
void ShowStuInfor(struct Student *h);
int title(char *a);

#endif

main.cpp文件代码:

#include "Function.h"

int main()
{
	int i,check;
	char Title[50];
	Student *head;
	title(Title);//把.txt文件第一行标题拷入Title数组中
	head = create();//提前创建一个结点,作为头指针
	openfile(head);//读取信息,将信息存入链表并计算总分和排名
	do
	{
		printf("                                                                                        n");
		printf("                                                                                        n");
		printf("                                                                                        n");
		printf("                                                                                        n");
		printf("                                                                                        n");
		printf("			********************************学生管理系统********************************n");
		printf("			*                                                                          *n");
		printf("			*您可以选择:                                                              *n");
		printf("			*          1:查询学生信息                                                  *n");
		printf("			*          2:修改学生信息                                                  *n");
		printf("			*          3:删除学生信息                                                  *n");
		printf("			*          4:显示学生信息                                                  *n");
		printf("			*          5:各科成绩个分数段人数                                          *n");
		printf("			*          0:退出系统                                                      *n");
		printf("			*                                                                          *n");
		printf("			****************************************************************************n");
		printf("		您选择:");
		scanf("%d",&i);
		if(getchar() == 'n')
		{
			switch(i)
			{
			case 1:
				{
					system("CLS");
					SearchStu(head,Title);//查找学生信息
					check = 0;
					break;
				}
			case 2:
				{
					system("CLS");
					ChangeInfor(head,Title);//改变学生信息
					ReCalculate(head);//信息改变后,总分和排名可能也改变了,重新计算总分
					ReRank(head);//重新计算排名
					check = 0;
					break;
				}
			case 3:
				{
					system("CLS");
					head = InforDelete(head,Title);//删除一整个学生信息,由于可能删除的是头指针,所以需要重新返回头指针
					ReRank(head);//删除信息后需要重新排名
					check = 0;
					break;
				}
			case 4:
				{
					system("CLS");
					printf("------------------------------------------------------n");
					printf("%s",Title);
					ShowStuInfor(head);//显示学生所有信息,包括排名和总分,并保存至data3.txt
					printf("------------------------------------------------------n");
					check = 0;
					break;
				}
			case 5:
				{
					system("CLS");
					printf("tt各科成绩个分数段人数nn");
					printf("-----------------------------------------------------------------------------n");
					ClassfyGrade(head);//各科分数分类并且保存于data2.txt
					printf("-----------------------------------------------------------------------------n");
					check = 0;
					break;
				}
			case 0:
				{
					system("CLS");
					printf("ttttt退出系统n");
					SaveNew(head,Title);//退出后保存修改后信息到data3.txt
					check = 1;
					break;
				}
			default:
				{
					printf("a");
					printf("输入错误,按任意键开始重新输入n");
					check = 0;
				
				}
			}
		}
		else
		{
			printf("输入不合法,请重新输入n");
		}

		if(check == 1)
		{
			break;
		}
		else
		{
			system("pause");
			system("CLS");
		}
		fflush(stdin);

	
	}while(1);
	return 0;
}

Function.cpp文件代码:

#include"Function.h"

//把data1.txt文件第一行标题读出来并保存于传入指针所指的数组中
int title(char *a)
{
	int i,j,n,k;
	FILE *fp1;
	struct Student *p1,*p2,*p3;
	if(( fp1 = fopen("data1.txt","r")) == NULL )//以读的方式打开文件data1.txt
	{
		printf("can't open filen");
		return -1;
	}
	fgets( a , 50 , fp1 );//把标题读出来存入数组title
	return 0;
}

//创建一个结点
//无传入参数,返回结点指针
struct Student *create()
{
	Student *p;
	p = (Student *)malloc(sizeof(struct Student));//开辟一个Student结构体空间
	p->next = NULL;
	return p;
}

//读取信息,将信息存入链表并计算总分和排名
//传入参数为链表头指针,返回值0或-1
int openfile(struct Student *h)
{
	int i,j,n,k;
	char title[50];
	FILE *fp1;
	struct Student *p1,*p2,*p3;
	if(( fp1 = fopen("data1.txt","r")) == NULL )//以读的方式打开文件data1.txt
	{
		printf("can't open filen");
		return -1;
	}
	fgets( title , 50 , fp1 );//把标题读出来存入数组title
	p2 = p1 = h;
	fscanf(fp1 ,"%d%s%f%f%f" ,&p1->id,&p1->name,&p1->Class[0],&p1->Class[1],&p1->Class[2]);
	p1->total = p1->Class[0] + p1->Class[1] + p1->Class[2];//计算总分
	p1->Rank = 1;//初始化排名
	i = 1;
	while( !feof(fp1) )
	{
		p1 = create();
	fscanf(fp1 ,"%d%s%f%f%f" ,&p1->id,&p1->name,&p1->Class[0],&p1->Class[1],&p1->Class[2]);
		p1->total = p1->Class[0] + p1->Class[1] + p1->Class[2];//计算总分
		p1->Rank = 1;//初始化排名
		p3 = h;
		for(j = 0; j < i;j++)//擂台法排名,p3从head开始
		{
			if((p1->total) > (p3->total))
			{
				p3->Rank = p3->Rank + 1;
			}
			else if((p1->total) < (p3->total))
			{
				p1->Rank = p1->Rank + 1;
			}
			p3 = p3->next;
		}
		p2->next = p1;//将前一个结点与新建结点链接起来
		p2 = p1;
		i++;
	}
	fclose(fp1);
	return 0;
}

//查找学生信息
void SearchStu(struct Student *h,char *title)
{
	char s[50],c;
	int check ,choose,ID,check3;
	struct Student *p;
	while(1)
	{
		check = 0;
		check3 = 0;	
		p = h;
		printf("tttt查询方式:nnttttt1.姓名查询nnttttt2.学号查询nntttt你的选择是:");
		scanf("%d",&choose);
		if(getchar() == 'n')
		{
			if(choose == 1)
			{
				printf("请输入您想查询学生的姓名:");
				scanf("%s",s);
				fflush(stdin);
				while(p)
				{
					if(strcmp(p->name , s ) == 0 )
					{
						printf("------------------------------------------------------n");
						printf("%s",title);
	printf("%dt%st%.2ft%.2ft%.2ft%.2ft  %dn",p->id ,p->name,p->Class[0],p->Class[1],p->Class[2],p->total,p->Rank);
						printf("------------------------------------------------------n");
						check = 1;
						
					}
					p = p->next;
				}
			}
			else if(choose == 2)
			{
				printf("请输入您想查询学生的学号:");
				scanf("%d",&ID);
				fflush(stdin);
				while(p)
				{
					if( p->id == ID )
					{
						printf("------------------------------------------------------n");
						printf("%s",title);
	printf("%dt%st%.2ft%.2ft%.2ft%.2ft  %dn",p->id ,p->name,p->Class[0],p->Class[1],p->Class[2],p->total,p->Rank);
						printf("------------------------------------------------------n");
						check = 1;
						break;
					}
					p = p->next;
				}
			}
			else
			{
				printf("输入错误,请重新输入!n");
				continue;
			}
			if(check == 0)
			{
				printf("找不到该同学信息!n");
			}
			while(1)
			{
				printf("是否再次查询(y / n)n");
				scanf("%c",&c);
				if(getchar() == 'n')
				{
					fflush(stdin);
					if( c == 'n'||c == 'N')
					{
						check3 = 1;
						break;
					}
					else if( c == 'y'||c == 'Y')
					{
						break;
					}
					else
					{
						printf("输入不合法,请重新输入n");
					}
				}
				else
				{
					printf("输入不合法,请重新输入n");
				}
				fflush(stdin);
			}
			if(check3 == 1)
			{
				break;
			}
			}
		else
		{
			printf("输入不合法,请重新输入n");
		}
		fflush(stdin);
		printf("n");
	}
}

//修改学生信息(姓名,科目一,科目二,科目三)
//传入参数为链表的头指针,无返回值
void ChangeInfor(struct Student *h,char *title)
{
	char s[50],choice,c,name;
	int check ,ID,choose,check2=0,check3 = 0;
	struct Student *p;
	while(1)
	{
		check = 0;
		check2 = 0;
		check3 = 0;
		p = h;
		while(1)
		{
			printf("tttt查询方式:nnttttt1.学生姓名nnttttt2.学生学号nntttt您的选择是:");
			scanf("%d",&choose);
			if(getchar() == 'n')
			{
				if(choose == 1)
				{
					printf("请输入您想修改信息的学生姓名:");
					scanf("%s",&s);
					fflush(stdin);
					//check2 = strcmp(h->name,s);
					break;
				}
				else if(choose == 2)
				{
					printf("请输入您想修改信息的学生学号:");
					scanf("%d",&ID);
					fflush(stdin);
					//check2 = (ID == h->id);
					break;
				}
				else
				{
					printf("输入不合法,请重新输入!n");
				}
			}
			else
			{
				printf("输入不合法,请重新输入n");
			}
			fflush(stdin);
		}
		while(p)
		{
			if(choose == 1)
			{
				check2 = !(strcmp(p->name,s));
			}
			else
			{
				check2 = (ID == p->id);
			}

			if(check2 )
			{
				printf("------------------------------------------------------n");
				printf("%s",title);
				printf("%dt%st%.2ft%.2ft%.2fn",p->id ,p->name,p->Class[0],p->Class[1],p->Class[2]);
				printf("------------------------------------------------------n");
				check = 1;
				printf("");
				while(1)
				{
					printf("是否修改学号?(y/Y or n/N)");
					scanf("%c",&choice);
					if(getchar() == 'n')
					{
						if(choice == 'Y' || choice == 'y')
						{
							printf("请输入新学号:");
							scanf("%d",&p->id );
							fflush(stdin);
							break;
						}
						else if(choice == 'N'||choice == 'n')
						{
							break;
						}
						else
						{
							printf("输入错误,请重新输入n");
						}
					}
					else
					{
						printf("输入不合法,请重新输入n");
					}
					fflush(stdin);
				}
				while(1)
				{
					printf("是否修改姓名?(y/Y or n/N)");
					scanf("%c",&choice);
					if(getchar() == 'n')
					{
						if(choice == 'Y' || choice == 'y')
						{
							printf("请输入新姓名:");
							scanf("%s",p->name );
							fflush(stdin);
							break;
						}
						else if(choice == 'N'||choice == 'n')
						{
							break;
						}
						else
						{
							printf("输入错误,请重新输入n");
						}
					}
					else
					{
						printf("输入不合法,请重新输入n");
					}
					fflush(stdin);
				}
				
				while(1)
				{
					printf("是否修改课程1成绩?(y/Y or n/N)");
					scanf("%c",&choice);
					if(getchar() == 'n')
					{
						if(choice == 'Y' || choice == 'y')
						{
							printf("请输入新成绩:");
							scanf("%f",&(p->Class[0]));
							fflush(stdin);
							break;
						}
						else if(choice == 'N'||choice == 'n')
						{
							break;
						}
						else
						{
							printf("输入错误,请重新输入n");
						}
					}
					else
					{
						printf("输入不合法,请重新输入n");
					}
					fflush(stdin);
				}
				
				while(1)
				{
					printf("是否修改课程2成绩?(y/Y or n/N)");
					scanf("%c",&choice);
					if(getchar() == 'n')
					{
						if(choice == 'Y' || choice == 'y')
						{
							printf("请输入新成绩:");
							scanf("%f",&(p->Class[1]));
							fflush(stdin);
							break;
						}
						else if(choice == 'N'||choice == 'n')
						{
							break;
						}
						else
						{
							printf("输入错误,请重新输入n");
						}
					}
					else
					{
						printf("输入不合法,请重新输入n");
					}
					fflush(stdin);
				}
				
				while(1)
				{
					printf("是否修改课程3成绩?(y/Y or n/N)");
					scanf("%c",&choice);
					if(getchar() == 'n')
					{
						if(choice == 'Y' || choice == 'y')
						{
							printf("请输入新成绩:");
							scanf("%f",&(p->Class[2]));
							fflush(stdin);
							break;
						}
						else if(choice == 'N'||choice == 'n')
						{
							break;
						}
						else
						{
							printf("输入错误,请重新输入n");
						}
					}
					else
					{
						printf("输入不合法,请重新输入n");
					}
					fflush(stdin);
				}
				//
			}
			p = p->next;//指向下一个节点
		}
		if(check == 0)
		{
			printf("找不到该同学信息!n");
		}
		while(1)
		{
			printf("是否再次修改(y / n)n");
			scanf("%c",&c);
			if(getchar() == 'n')
			{
				
				if( c == 'n'||c == 'N')
				{
					check3 = 1;
					break;
				}
				else if( c == 'y'||c == 'Y')
				{
					break;
				}
				else
				{
					printf("输入不合法,请重新输入n");
				}
			}
			else
			{
				printf("输入不合法,请重新输入n");
			}
			fflush(stdin);
		}
		if(check3 == 1)
		{
			break;
		}
		printf("n");
	}
}

//不同分数段的各科分数进行分段,然后记录并保存在data2文件中
//传入参数为链表头指针,返回值为0(正常结束)或-1(文件打开失败)
int ClassfyGrade(struct Student *h)
{
	int A[ClassNum],B[ClassNum],C[ClassNum],D[ClassNum],E[ClassNum],s[5],i,TotalP=0;
	FILE *fp;
	double grade,sum = 0,average,a,max = 0,min = 100;
	struct Student *p;
	if(( fp = fopen("data2.txt","w")) == NULL )
	{
		printf("can't open filen");
		return -1;
	}
	printf("t100~90t89~80t79~70t69~60t不及格t总人数t平均分t最高分t最低分nn");
	fprintf(fp,"tt 100~90t  89~80t  79~70t  69~60t  不及格t  总人数t  平均分t  最高分t  最低分nn");
	for(i = 0 ;i < ClassNum ; i++)//i用来分别调用三科成绩
	{
		p = h;
		sum = 0;
		max = 0;
		min = 100;
		TotalP = 0;
		A[i] = B[i] = C[i] = D[i] = E[i] = 0;
		while(p)
		{
			grade = p->Class[i];
			if( grade<=100 && grade>=90 )
			{
				A[i] = A[i] + 1;
			}
			else if( grade<=89 && grade>=80 )
			{
				B[i] = B[i] + 1;
			}
			else if( grade<=79 && grade>=70 )
			{
				C[i] = C[i] + 1;
			}
			else if( grade<=69 && grade>=60 )
			{
				D[i] = D[i] + 1;
			}
			else
			{
				E[i] = E[i] + 1;
			}
			a = grade;
			if(a > max)
			{
				max = a;
			}
			else if( a < min)
			{
				min = a;
			}
			sum =sum + grade;
			TotalP++;//总人数
			p = p->next;//指向下一个节点
		}
		printf("课程%d",i+1);
		printf("t%d",A[i]);
		printf("t%d",B[i]);
		printf("t%d",C[i]);
		printf("t%d",D[i]);
		printf("t%d",E[i]);
		printf("t%d",A[i]+B[i]+C[i]+D[i]+E[i]);
		printf("t%.2f",sum / TotalP );
		printf("t%.2f",max);
		printf("t%.2fn",min);
		printf("n");
		fprintf(fp,"课程%d",i+1);
		fprintf(fp,"tt%d",A[i]);
		fprintf(fp,"ttt%d",B[i]);
		fprintf(fp,"ttt%d",C[i]);
		fprintf(fp,"ttt%d",D[i]);
		fprintf(fp,"ttt%d",E[i]);
		fprintf(fp,"ttt%d",A[i]+B[i]+C[i]+D[i]+E[i]);
		fprintf(fp,"  tt%.2f",sum / TotalP );
		fprintf(fp,"   t%.2f",max);
		fprintf(fp,"   t%.2fnn",min);
		fprintf(fp,"n");
		//p = h;//重新赋予头指针,便于从头开始索引下一科目成绩
		
	}
	s[0] = A[0] + A[1] + A[2];
	s[1] = B[0] + B[1] + B[2];
	s[2] = C[0] + C[1] + C[2];
	s[3] = D[0] + D[1] + D[2];
	s[4] = E[0] + E[1] + E[2];
	printf("总人数t%dt%dt%dt%dt%dt%dn",s[0],s[1],s[2],s[3],s[4],s[0]+s[1]+s[2]+s[3]+s[4]);
	fprintf(fp,"总人数tt%dttt%dttt%dttt%dttt%dttt%dn",s[0],s[1],s[2],s[3],s[4],s[0]+s[1]+s[2]+s[3]+s[4]);
	return 0;
}

//删除学生信息
//传入参数为链表头指针,返回值为链表头指针
struct Student *InforDelete(struct Student *h ,char *title)
{
	char s[100],c;
	int check,ID,choose,check2,check3;//用于检测是否找到学生
	struct Student *p1,*p2,*p3,*p4; 
	p1 = h;
	while(1)
	{
		check = 0;
		check3 = 0;
		p3 = h;
		while(1)
		{
			printf("tttt查询方式:nnttttt1.姓名查询nnttttt2.学号查询nntttt您的选择是:");
			scanf("%d",&choose);
			if(getchar() == 'n')
			{
				if(choose == 1 || choose == 2)
				{
					fflush(stdin);
					break;
				}
				else
				{
					printf("输入错误,请重新输入n");
				}
			}
			else
			{
				printf("输入错误,请重新输入n");
			}
			fflush(stdin);
		}
		if(choose == 1)
		{
			printf("请输入需要删除的学生姓名:");
			scanf("%s",s);
			fflush(stdin);
			while(p3)//查找同名的学生
			{
				if(strcmp(p3->name,s) == 0)
				{
					check = 1;
					printf("------------------------------------------------------n");
					printf("%s",title);
printf("%dt%st%.2ft%.2ft%.2fn",p3->id ,p3->name,p3->Class[0],p3->Class[1],p3->Class[2]);
					printf("------------------------------------------------------n");

					while(1)
					{
						printf("是否要删除该学生(y / n)n");
						check2 = 0;
						scanf("%c",&c);
						if(getchar() == 'n')
						{
							fflush(stdin);
							if( c == 'n'||c == 'N')
							{
								
								break;
							}
							else if( c == 'y'||c == 'Y')
							{
								check2 = 1;
								break;
							}
							else
							{
								printf("输入不合法,请重新输入n");
							}
						}
						else
						{
							printf("输入不合法,请重新输入n");
						}
						fflush(stdin);
					}
					if(check2 == 1)
					{
						if(p1 == p3)//如果删除的是头结点
						{
							p2 = p3;
							p4 = p3->next;//p2指向下一个结点
							printf("%s已经被删除n",p3->name);
							free(p2);
							h = p4;//返回第二个结点的指针,作为头结点
						}
						else
						{
							p2 = p3;
							p3 = p3->next;
							p1->next = p3;//将被删除结点且一个结点的next指针指向被删除结点的下一个结点
							printf("%s已经被删除n",p2->name);
							free(p2);
						}
					}
				}
				p1 = p3;
				p3 = p3->next;
			}
		}
		else if(choose == 2)
		{
			printf("请输入需要删除的学生学号:");
			scanf("%d",&ID);
			if(getchar() == 'n' )
			{
				//fflush(stdin);
				while(p3)//查找同名的学生
				{
					if(p3->id == ID)
					{
						check = 1;
						break;//如果第一次循环就跳出,说明删除的是头指针,此时p1和h都指向头结点
							  //如果是其他时候跳出,那么h指向要删除的结点,p1指向前一个结点
					}
					p1 = p3;
					p3 = p3->next;
				}
				if(check == 1)//如果找到该学生
				{
					if(p1 == p3)//如果删除的是头结点
					{
						p2 = p3->next;//p2指向下一个结点
						printf("%s已经被删除n",p3->name);
						free(p3);
						return p2;//返回第二个结点的指针,作为头结点
					}
					else
					{
						p2 = p3->next;
						p1->next = p2;//将被删除结点且一个结点的next指针指向被删除结点的下一个结点
						printf("%s已经被删除n",p3->name);
						free(p3);
					}
				}
				else
				{
					printf("未找到该同学n");
				}
			}
			else
			{
				printf("输入不合法n");
			}
			fflush(stdin);

		}
		else
		{
			printf("输入错误n");
		}
		while(1)
		{
			printf("是否再次删除(y / n)n");
			scanf("%c",&c);
			if(getchar() == 'n')
			{
				fflush(stdin);
				if( c == 'n'||c == 'N')
				{
					check3 = 1;
					break;
				}
				else if( c == 'y'||c == 'Y')
				{
					break;
				}
				else
				{
					printf("输入不合法,请重新输入n");
				}
			}
			else
			{
				printf("输入不合法,请重新输入n");
			}
			fflush(stdin);
		}
		if(check3 == 1)
		{
			break;
		}
		printf("n");
	}
	return h;
}

//重新计算学生总分
//传入参数为链表头指针,无返回值
void ReCalculate(struct Student *h)
{
	struct Student *p;
	p = h;
	while(p)
	{
		p->total = p->Class[0] + p->Class[1] + p->Class[2];
		p = p->next;
	}
}

//重新排名
void ReRank(struct Student *h)
{
	struct Student *p1,*p3;
	int j = 0 , i = 1;
	p1 = h;
	p1->Rank = 1;
	p1 = h->next;
	while(p1)
	{
		p1->Rank = 1;
		p3 = h;
		for(j = 0; j < i;j++)//擂台法排名,p3从head开始,一直比到p3与p1指向同一个结点就结束循环
		{
			if((p1->total) > (p3->total))
			{
				p3->Rank = p3->Rank + 1;
			}
			else if((p1->total) < (p3->total))
			{
				p1->Rank = p1->Rank + 1;
			}
			p3 = p3->next;
		}
		i++;
		p1 = p1->next;
	}
}

//保存修改后的信息到data3.txt
int SaveNew(struct Student *h , char *s)
{
	FILE *fp;
	struct Student *p;
	if(( fp = fopen("data3.txt","w")) == NULL )//在指定位置建立一个新的txt文件
	{
		printf("can't bulid filen");
		return -1;
	}
	p = h;
	fputs(s,fp);
	while(p)
	{
fprintf(fp,"%dt%st%.2ft%.2ft%.2ft%.2ft  %dn",p->id,p->name,p->Class[0],p->Class[1],p->Class[2],p->total,p->Rank);
		p = p->next;
	}
	fclose(fp);
	return 0;
}

//显示学生全部信息
void ShowStuInfor(struct Student *h)
{
	struct Student *p;
	p = h;
	while(p)
	{
	 printf("%dt%st%.2ft%.2ft%.2ft%.2ft  %dn",p->id,p->name,p->Class[0],p->Class[1],p->Class[2],p->total,p->Rank);
		p = p->next ;
	}
}

学生成绩管理系统显示
  1. 菜单
  2. 查询
  3. 修改
  4. 删除
  5. 显示所有人信息
  6. 各科分数段人数统计
  7. 退出
  8. 数据样式(data1.txt)
  9. 数据样式(data2.txt)

  1. 数据样式(data3.txt)
转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/330091.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号