文档章节

Algorithm: 学生成绩管理系统

SHIHUAMarryMe
 SHIHUAMarryMe
发布于 2016/06/25 01:48
字数 1762
阅读 132
收藏 5

 

C++学生成绩管理系统
编写一个统计存储在文件中的学生成绩管理程序。设学生成绩以一个学生一条记录的形式存储在文件中。每个学生记录的信息有姓名﹑学号和各门功课的成绩。
功能如下:
1. 求各门课程的总分﹑平均分。
2.按姓名寻找记录并显示。
3.  按学号寻找记录并显示。
4.查询全部学生成绩。
5.按总分由高到低显示学生信息。        
提示:设每位学生语文﹑数学﹑英语3门课程。主程序输入文件名后,进入接受命令﹑执行命令处理程序循环。
按问题的要求共设5条命令:
 1. 求各门课程的总分。
2.求各门课程的平均分。
 3.按姓名寻找记录并显示。
 4.  按学号寻找记录并显示。
 5.结束命令
为求各门课程的总分,从文件中逐一读出学生记录。累计各门课程的分数,待文件处理完即可得到各门课程的总分。为求各门课程的平均分,从文件中逐一读出学生记录。累计各门课程的分数。并统计学生人数,待文件处理完毕,将得到的各门课程的平均分。按学生名字寻找学生信息的处理,首先要求输入待寻找学生的名字,顺序读入学生记录。凡名字与待寻找学生的名字相同的记录在屏幕上显示,直到文件结束。按学生学号寻找学生信息的处理,首先要求输入待寻找学生的学号,顺序读入学生记录。凡学号与待寻找学生的学号相同的记录在屏幕上显示,直到文件结束。浏览学生全部成绩,顺序读入学生记录。并在屏幕上显示,直到文件结束。按总分由高到低显示学生信息。顺序读入学生记录并构造一个有序链表。然后显示链表上的元素

 

/* minGW 4.8.1及以上版本编译器下编译 */
#include <iostream>
#include <fstream>
#include <string>
#include <algorithm>
#include <string>
#include <type_traits>
#include <array>

enum Subject : int{
	Chinese = 0,
	Math = 1,
	English = 2
};

template<typename T>
typename std::remove_reference<T>::type&& my_move(T&& value)noexcept
{
	using type = typename std::remove_reference<T>::type&&;
	return static_cast<type>(value);
}


class StudentInfo{
	private:
		std::string name_;
		std::string id_;
		int chinese_; 
		int math_;
		int english_;
		
		inline int& getChineseScore()noexcept
		{
			return (this->chinese_);
		}
		
		inline int getChineseScore()const noexcept
		{
			return (this->chinese_);
		}
		
		inline int& getMathScore()noexcept
		{
			return (this->math_);
		}
		
		inline int getMathScore()const noexcept
		{
			return (this->math_);
		}
		
		inline int& getEnglishScore()noexcept
		{
			return (this->english_);
		}
		
		inline int getEnglishScore()const noexcept
		{
			return (this->english_);
		}
		
		using array = int& (StudentInfo::*)()noexcept;
		using cArray = int (StudentInfo::*)()const noexcept;
		
		array functionArray[3] = {&StudentInfo::getChineseScore, &StudentInfo::getMathScore, &StudentInfo::getEnglishScore};
		
		cArray functionCArray[3] = {static_cast<cArray>(&StudentInfo::getChineseScore), static_cast<cArray>(&StudentInfo::getMathScore), 
		                            static_cast<cArray>(&StudentInfo::getEnglishScore)};
		
		public:
			
			StudentInfo()=default;
			StudentInfo(const std::string& name, const std::string& id, const int& chinese=0, const int& math=0, const int& english=0);
			~StudentInfo()=default;
			
			StudentInfo(const StudentInfo& other);
			StudentInfo(StudentInfo&& other);
			StudentInfo& operator=(const StudentInfo& other);
			StudentInfo& operator=(StudentInfo&& other);
			int& getScore(const Subject& obj)noexcept;
			int  getScore(const Subject& obj)const noexcept;
			
			inline std::string& getId()noexcept
			{
				return (this->id_);
			}
			
			inline std::string getId()const noexcept
			{
				return (this->id_);
			}
			
			friend bool operator==(const StudentInfo& lh, const StudentInfo& rh)noexcept;
			friend std::ostream& operator<<(std::ostream& os, const StudentInfo& student);
			
};

StudentInfo::StudentInfo(const std::string& name, const std::string& id, const int& chinese, const int& math, const int& english)
            :name_(name),
             id_(id),
             chinese_(chinese),
             math_(math),
             english_(english)
{
	//constructor.
}

StudentInfo::StudentInfo(const StudentInfo& other)
            :name_(other.name_),
             id_(other.id_),
             chinese_(other.chinese_),
             math_(other.math_),
             english_(other.english_)
{
	//copy-constructor.
}

StudentInfo::StudentInfo(StudentInfo&& other)
            :name_(my_move(other.name_)),
             id_(my_move(other.id_)),
             chinese_(my_move(other.chinese_)),
             math_(my_move(other.math_)),
             english_(my_move(other.english_))
{
	//move-constructor.
}

StudentInfo& StudentInfo::operator=(const StudentInfo& other)
{

		this->name_ = other.name_;
		this->id_ = other.id_;
		this->chinese_ = other.chinese_;
		this->math_ = other.math_;
		this->english_ = other.english_;
	
	return *this;
}

StudentInfo& StudentInfo::operator=(StudentInfo&& other)
{
	this->name_ = my_move(other.name_);
	this->id_ = my_move(other.id_),
	this->chinese_ = my_move(other.chinese_);
	this->math_ = my_move(other.math_),
	this->english_ = my_move(other.english_);
	
	return *this;
}

std::ostream& operator<<(std::ostream& os, const StudentInfo& student)
{
	os<< student.name_ << " " << student.id_ << " " << student.chinese_ << " "
	  << student.math_ << " " << student.english_;
	  
	  return os;
}

int& StudentInfo::getScore(const Subject& obj)noexcept
{
	return (this->*functionArray[static_cast<int>(obj)])(); //注意这里->*,因为是成员函数的指针. 
}


int StudentInfo::getScore(const Subject& obj)const noexcept
{
	int index = static_cast<int>(obj);
	return (this->*functionCArray[index])();
}

bool operator==(const StudentInfo& lh, const StudentInfo& rh)noexcept
{
	if(lh.id_ == rh.id_){
		return true;
	}
	
	return false;
}

class RWFile{
	private:
		
		class FindObject{
			private:
				std::pair<std::string, std::string> getNameAndId(const std::string& sTr)noexcept //获得名字. 
				{
					std::pair<std::string, std::string> nameAndID;
					
					std::string name;
					std::string ID;
					std::size_t indexS;
					std::size_t indexE;
					
					if(!sTr.empty()){
						std::runtime_error(std::string("Cant not get data!"));
					}
					
					indexS = sTr.find(std::string("姓名"));
					indexE = sTr.find_first_of(" ");
					
					name = sTr.substr(indexS, indexE);
					indexS = name.find_first_of(":");
					name = name.substr(indexS + 1);
					
					nameAndID.first = name; //获得名字.
					
					indexS = sTr.find(std::string("学号"));
					name = sTr.substr(indexS);
					indexS = name.find_first_of(":");
					indexE =  name.find_first_of(" ");
					ID = name.substr(indexS+1, indexE);
					indexE = ID.find_first_of(" ");
					ID = ID.substr(0, indexE);
					
					nameAndID.second = ID;  //保存获得的ID. 
					
					return nameAndID;
				}
				
				std::array<int, 3> getScore(const std::string& sTr)noexcept
				{
					std::array<int, 3> scores; //保存各个学科的成绩.
					std::string scoreStr;
					std::size_t indexS;
					std::size_t indexE;
					
					if(!sTr.empty()){
						std::runtime_error(std::string("Can not read data!"));
						
					} 
					
					indexS = sTr.find_first_of(std::string("语文"));
					scoreStr = sTr.substr(indexS);
					indexS = scoreStr.find_first_of(":");
					indexE = scoreStr.find_first_of(" ");
					scoreStr = scoreStr.substr(indexS+1, indexE);
					indexE = scoreStr.find_first_of(" ");
					scoreStr = scoreStr.substr(0, indexE);
					
					scores[0] = std::stod(scoreStr);  //存储语文成绩.
					
					indexS = sTr.find_first_of(std::string("数学"));
					scoreStr = sTr.substr(indexS);
					indexS = scoreStr.find_first_of(":");
					indexE = scoreStr.find_first_of(" ");
					scoreStr = scoreStr.substr(indexS+1, indexE);
					indexE = scoreStr.find_first_of(" ");
					scoreStr = scoreStr.substr(0, indexE);
					
					scores[1] = std::stod(scoreStr);  //存储数学成绩.
					
					indexS = sTr.find_last_of(":");
					scoreStr = sTr.substr(indexS+1);
					
					scores[2] = std::stod(scoreStr);  //存储英语成绩. 
					
				}
				
			public:
				FindObject()=default;
				~FindObject()=default;
				
				StudentInfo operator()(const std::string& sTr)  //构建学生信息. 
				{
					std::pair<std::string, std::string> pair = this->getNameAndId(sTr);
					std::array<int, 3> array = this->getScore(sTr);
					
					StudentInfo student(pair.first, pair.second, array[0], array[1], array[2]);
					
					return student;
				}
		};
		
		std::vector<StudentInfo> students_{};
		std::string file_name_;
		std::ifstream read_txt_;    //读取txt文件里的内容读取完毕后txt文件为空.
		std::ofstream write_txt_;   //写入内容到txt文件中. 
		std::fstream stream_;       //读取文件中的内容但是不会修改原来txt中的内容. 
		
		//std::pair<object, std::vector<double>> average_{};          //该学科的所有同学的成绩. 
		//std::pair<name, std::vector<StudentInfo>> name_search_{};  //姓名索引.
		//std::pair<id, StudentInfo> id_search{};                   //id索引
		
		void readContents();
		void closeDoc()noexcept;
		void saveContentToDoc()noexcept;
		 
		
		public:
			using ID = std::string;
			using name = std::string;
			using object = std::string;
			
			RWFile();
			RWFile(const std::string& txt);
			~RWFile()=default;
			RWFile(const RWFile& other) = delete;
			RWFile& operator=(const RWFile& other) = delete;
			
			void searchObjectAverage(const Object& obj);
			//void searchID(const std::string& idStr);
			//void searchName(const std::string& nameStr);
			void showAllBody()const noexcept;
			void changeScore(const double& realScore, const std::string& id, const Object& obj);
};

RWFile::RWFile()
       :file_name_(std::string(""))
{
	std::cout<< "Please enter the name of t(e)xt:  "<<std::endl;
	std::cin>> (this->file_name_);
	
	(this->stream_).open(this->file_name_);
	if(!(this->stream_).is_open()){
		std::cout<< "There is not this text: "<< (this->file_name_)<< ".  Plese enter again"<<std::endl;
		std::cin>>(this->file_name_);
		(this->stream_).open(this->file_name_);
		(this->stream_).close();
	}
	
	this->readContents();
}

RWFile::RWFile(const std::string& txt)try
       :file_name_(txt)
{
	(this->stream_).open(this->file_name_);
	if(!(this->stream_).is_open()){
		throw std::runtime_error(std::string("Please give a conrrect name!"));
	}
	(this->stream_).close();
	
	this->readContents();
	
}catch(const std::runtime_error& error){
	std::cout<< error.what() <<std::endl;
}

void RWFile::readContents()
{
	FindObject find;
	std::string str;
	
	(this->read_txt_).open(this->file_name_, std::fstream::out);
	while(getline((this->read_txt_), str)){   //读取txt文件. 
		
		StudentInfo student = find(str);
		(this->students_).push_back(student);
	}
	
	(this->students_).shrink_to_fit();
	(this->read_txt_).close();
}

void RWFile::searchObjectAverage(const Subject& obj)
{
	int totalScore;
	
	if(!(this->students_).empty()){
		for(const StudentInfo& student : (this->students_)){
			
			totalScore += (student.getScore(obj));
			
		}
	}
	 
	std::cout<< "This object total score: " << totalScore <<std::endl;
	std::cout<< "The average of this object: " << totalScore/(this->students_).size() <<std::endl;
}

void RWFile::changeScore(const double& realScore, const std::string& id, const Object& obj)
{
	if(!(this->students_).empty()){
		
		for(StudentInfo& student : (this->students_)){
			if(id == student.getId()){
				student.getScore(obj) = realScore;
			}
		}
	}
	
	this->saveContentToDoc();
}

void RWFile::closeDoc()noexcept
{
	if(!(this->stream_).is_open()){
		(this->stream_).close();
	}
	
	if(!(this->read_txt_).is_open()){
		(this->read_txt_).close();
	}
	
	if(!(this->write_txt_).is_open()){
		(this->write_txt_).close();
	}
}

void RWFile::saveContentToDoc()noexcept
{
	(this->write_txt_).open(this->file_name_, std::ofstream::in);
	
	if((this->write_txt_).is_open() && !(this->students_).empty()){
		for(const StudentInfo& info : (this->students_)){
			(this->write_txt_) << info << '\n';
		}
	}
	
}

void RWFile::showAllBody()const noexcept
{
	if(!(this->students_).empty()){
		for(const StudentInfo student : (this->students_)){
			std::cout<< student <<std::endl;
		}
	}
}

int main()
{
	std::string ID("013");
	std::string Dir("成绩.txt");
	RWFile system(Dir);
	
	system.showAllBody();
	system.searchObjectAverage(Object::Math);
	system.changeScore(150, ID, Object::Math);
	
	return 0;
}

 

© 著作权归作者所有

SHIHUAMarryMe
粉丝 13
博文 162
码字总数 138435
作品 0
武汉
程序员
私信 提问
这个用Java要怎么写代码?

*6 学籍管理系统 6.1 功能要求: 1. 学生注册登记 提供给系统最基本的学籍信息。 2. 学生成绩登记 按专业分类,以年级为单位,登记学生在校期间每门课程的成绩。 3. 学籍更改登记 包括简历...

c82684253
2013/12/24
791
10
学生成绩管理系统

JDK 1.6+ 平台有学生管理、学校管理、教师管理、课程年级管理、作业管理、信息发布、考试管理、成绩查询、报表展示、系统管理等模块。功能涵盖了教务系统所有功能。 Tomcat 6+/JBoss 4.2+ M...

木辰风语者
2016/06/16
12
0
因挂科,电信专业学生侵入学校系统改分被开除,Python黑客手段!

一名大四学生由于在校不努力,门门考试挂科而入侵学校数据库,并修改成绩至合格线以上。 经该校研究决定,给予该生开除处分。 该大四学生为该校电信专业学生。该生利用学校教务系统的漏洞,通...

Python新世界
2018/07/26
0
0
急求,高手帮忙,成绩管理系统

使用c++语言编写 设计题目:6、成绩管理系统 (限最多5人完成) 现有学生成绩信息,内容如下 姓名 学号 语文 数学 英语 张明明 01 67 78 82 李成友 02 78 91 88 张辉灿 03 68 82 56 王露 04...

wangjungang293
2010/06/11
412
12
学生成绩管理系统(C/C++语言)

某班级有学生若干人,学生的信息包括姓名、学号、进入系统的口令,该班级本学期开设4门课程,写一个程序,供3种人用: (1)班主任(老师编号、口令)用它可查看每位同学各门课程的总评成绩(...

做梦的人
2014/01/06
874
6

没有更多内容

加载失败,请刷新页面

加载更多

NIO基于长度域的报文在Netty下的解码

1, 先复习一下粘包/拆包 1.1, 粘包/拆包的含义 TCP是个“流”协议, 并不了解上层业务数据的具体含义, 它会根据TCP缓冲区的实际情况进行包的划分,所以在业务上认为,一个完整的包可能会被TCP...

老菜鸟0217
今天
8
0
从零开始搭建spring-cloud(2) ----ribbon

在微服务架构中,业务都会被拆分成一个独立的服务,服务与服务的通讯是基于http restful的。Spring cloud有两种服务调用方式,一种是ribbon+restTemplate,另一种是feign。 其实我们已经在上...

Vincent-Duan
今天
17
0
get和post的区别?

doGet:路径传参。效率高,安全性差(get的传送数据量有限制,不能大于2Kb) doPOST:实体传参。效率低,安全性好 建议: 1、get方式的安全性较Post方式要差些,包含机密信息的话,建议用Pos...

花无谢
昨天
4
0
当谈论迭代器时,我谈些什么?

当谈论迭代器时,我谈些什么? 花下猫语:之前说过,我对于编程语言跟其它学科的融合非常感兴趣,但我还说漏了一点,就是我对于 Python 跟其它编程语言的对比学习,也很感兴趣。所以,我一直...

豌豆花下猫
昨天
14
0
10天学Python直接做项目,我做了这5件事

初学者如何尽快上手python? 市面上关于如何学python的资料很多,但是讲的都太复杂。 我就是很简单的几句话,从小白到开发工程师,我只做了五件事。 我觉得任何商业计划书如果不能用几句话讲...

Python派森
昨天
7
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部