学生成绩管理系统
现有学生成绩信息文件1(1.txt),内容如下
姓名 学号 语文 数学 英语
张明明 01 67 78 82
李成友 02 78 91 88
张辉灿 03 68 82 56
王露 04 56 45 77
陈东明 05 67 38 47
学生成绩信息文件2(2.txt),内容如下:
姓名 学号 语文 数学 英语
陈果 31 57 68 82
李华明 32 88 90 68
张明东 33 48 42 56
李明国 34 50 45 87
陈道亮 35 47 58 77
试编写一管理系统,要求如下:
1) 实现对两个文件数据进行合并,生成新文件3.txt
2) 抽取出三科成绩中有补考的学生并保存在一个新文件4.txt
3) 对合并后的文件3.txt中的数据按总分降序排序(至少采用两种排序方法实现)
4) 输入一个学生姓名后,能查找到此学生的信息并输出结果(至少采用两种查找方法实现)
5) 要求使用结构体,链或数组等实现上述要求.
#ifndef _LIST_H_
#define _LIST_H_
#include <string> // handle string
#include <iostream> // Input/Output stream
#include <iomanip> // I/O manipulate
#include <fstream> // handle file stream
using namespace std;
typedef struct ElemType{
string name; // 姓名
string id; // 学号
double Chinese; // 语文
double Mathematics; // 数学
double English; // 英语
}Person;
typedef struct Node{
Person data; // 数据域
struct Node *pNext; // 指针域
}node;
class List{
public:
List();
int Length();
bool Insert(int iPos, Person elem);
bool Delete(int iPos, Person& elem);
bool GetElem(int iPos, Person& elem);
bool SetElem(int iPos, Person& elem);
bool fromFile(char* szFile);
bool toFile(char* szFile);
bool SortName();
bool isEmpty();
bool Clear();
int BinarySearch(string name);
void Show(int iPos);
void Traverse();
~List();
private:
node* head;
};
#endif //_LIST_H_
#include "List.h"
/*
Parameter : none
Return : none
Description : class default constructor
*/
List::List() {
cout<<"class default constructor... "<<endl;
head = new Node;
head->pNext = NULL;
} // List
/*
Parameter : int , Person
Return : true or false
Description : insert an element at the iPos destination position
*/
bool List::Insert(int iPos, Person elem) {
int i = 0;
Node* p = head;
Node* q = new Node;
// search for the destination position
while (p && i < iPos - 1) {
p = p->pNext;
i++;
}
// less than or more than list length
if (!p || i > iPos - 1) {
cout<<"less than or more than list length!"<<endl;
return false;
}
// insert the element to the destination
q->data = elem;
q->pNext = p->pNext;
p->pNext = q;
return true;
} // Insert
/*
Parameter : int , Person&
Return : true or false
Description : get the data form position
*/
bool List::GetElem(int iPos, Person& elem) {
int i = 0;
Node* p = head->pNext;
if (iPos < 1 || iPos > Length()) {
cout<<"wrong position in GetElem function ... "<<endl;
return false;
}
while (p && i < iPos - 1) {
p = p->pNext;
i++;
}
if (!p || i > iPos - 1) {
cout<<"less than or more than list length..."<<endl;
return false;
}
elem = p->data;
return true;
} // GetElem
/*
Parameter : int, Person&
Return : true or false
Description : set the element of position iPos
*/
bool List::SetElem(int iPos, Person& elem) {
int i = 0;
Node* p = head->pNext;
if (iPos < 1 || iPos > Length()) {
cout<<"wrong position in SetElem function..."<<endl;
return false;
}
while (p && i < iPos - 1) {
p = p->pNext;
i++;
}
if (!p || i > iPos - 1) {
cout<<"less than or more than list length..."<<endl;
return false;
}
p->data = elem;
return true;
} // SetElem
/*
Parameter : int
Return : none
Description : show a student information in position
*/
void List::Show(int iPos) {
Person anonymous;
GetElem(iPos, anonymous);
cout<<"=============information============="<<endl;
cout<<"姓名"<<setw(8)<<"学号"<<setw(8)<<"语文"<<setw(8)<<"数学"<<setw(8)<<"英语"<<endl;
cout<<anonymous.name<<setw(6);
cout<<anonymous.id<<setw(8);
cout<<anonymous.Chinese<<setw(8);
cout<<anonymous.Mathematics<<setw(8);
cout<<anonymous.English<<endl;
cout<<"====================================="<<endl;
} // Show
/*
Parameter : none
Return : none
Description : traverse the list
*/
void List::Traverse() {
Node* p = head->pNext;
cout<<"-------------------------------------"<<endl;
cout<<"姓名"<<setw(8)<<"学号"<<setw(8)<<"语文"<<setw(8)<<"数学"<<setw(8)<<"英语"<<endl;
while (p) {
cout<<p->data.name<<setw(6);
cout<<p->data.id<<setw(6);
cout<<p->data.Chinese<<setw(6);
cout<<p->data.Mathematics<<setw(6);
cout<<p->data.English<<endl;
p = p->pNext;
}
cout<<"====================================="<<endl;
} // Traverse
/*
Parameter : none
Return : if empty return true
Description : if list is empty will return true or return false
*/
bool List::isEmpty() {
if (Length()) {
return false;
} else {
return true;
}
} // isEmpty
/*
Parameter : char*
Return : true or false
Description : get data from file
*/
bool List::fromFile(char* szFile) {
Person anonymous;
ifstream file(szFile);
if(!file.is_open()) {
cout<<" file open failed... "<<endl;
return false;
} else {
cout<<"reading data from file "<<szFile<<"... "<<endl;
}
while (getline(file, anonymous.name, '/n')) {
file>>anonymous.name>>anonymous.id>>anonymous.Chinese>>anonymous.Mathematics>>anonymous.English;
Insert(1, anonymous);
}
return true;
} // fromFile
/*
Parameter : char*
Return : true or false
Description : store data to a file
*/
bool List::toFile(char* szFile) {
ofstream file(szFile);
if (!file.is_open()) {
cout<<"open file failed ... "<<endl;
return false;
} else {
cout<<"writing data to file "<<szFile<<"... "<<endl;
}
file<<"姓名"<<setw(8);
file<<"学号"<<setw(8);
file<<"语文"<<setw(8);
file<<"数学"<<setw(8);
file<<"英语"<<endl;
Node* p = head->pNext;
while (p) {
file<<p->data.name<<setw(6);
file<<p->data.id<<setw(8);
file<<p->data.Chinese<<setw(8);
file<<p->data.Mathematics<<setw(8);
file<<p->data.English<<endl;
p = p->pNext;
}
return true;
} //toFile
/*
Parameter : none
Return : list length
Description : get list length
*/
int List::Length() {
Node* p = head->pNext;
int iLen = 0;
while (p) {
p = p->pNext;
iLen++;
}
return iLen;
} // Length
/*
Parameter : none
Return : true or false
Description : use straight insertion sort method sort the list data according to name
*/
bool List::SortName() {
Person current;
Person previous;
for (int i = 2; i < Length(); ++i) {
GetElem(i, current);
for (int j = i; j > 1; --j) {
GetElem(j-1, previous);
if (current.name.compare(previous.name) < 0 ) {
SetElem(j, previous);
SetElem(j-1, current);
}
}
}
return true;
} // nameSort
/*
Parameter : string
Return : int : person position
Description : use binary search method to search a student then display his information
*/
int List::BinarySearch(string name) {
SortName(); // first make the list in order
int iLow = 1; // 置区间初值
int iHigh = Length();
int iMiddle = 1;
Person anonymous;
while (iLow <= iHigh) {
iMiddle = (iLow + iHigh) / 2;
GetElem(iMiddle, anonymous);
if (anonymous.name.compare(name) == 0) {
return iMiddle; // find the person, return his position in the list
} else if (anonymous.name.compare(name) < 0) {
iLow = iMiddle + 1;
} else {
iHigh = iMiddle - 1;
}
}
return -1;
} // BinarySearch
/*
Parameter : none
Return : none
Description : class default destructor
*/
List::~List() {
cout<<"class default destructor ... "<<endl;
delete head;
} // ~List
#include "List.h"
int main(int argc, char *argv[])
{
List list;
list.fromFile("1.txt");
list.fromFile("2.txt");
//1) 实现对两个文件数据进行合并,生成新文件3.txt
list.toFile("3.txt");
//2) 抽取出三科成绩中有补考的学生并保存在一个新文件4.txt
List fail;
Person anonymous;
for (int i = 1; i <= list.Length(); ++i) {
list.GetElem(i, anonymous);
if (anonymous.Chinese < 60 || anonymous.Mathematics < 60 || anonymous.English < 60 ) {
fail.Insert(1, anonymous);
}
}
fail.toFile("4.txt");
//3) 对合并后的文件3.txt中的数据按总分降序排序
//4) 输入一个学生姓名后,能查找到此学生的信息并输出结果, 采用折半查找法
string name;
int iPos;
cout<<"输入学生姓名 : ";
cin>>name;
iPos = list.BinarySearch(name);
if (iPos > 0) {
list.Show(iPos);
} else {
cout<<"无 "<<name<<" 的数据信息!"<<endl;
}
list.Traverse();
return 0;
}