404 lines
12 KiB
C++
404 lines
12 KiB
C++
#include <iostream>
|
|
#include <iomanip>
|
|
#include <fstream>
|
|
#include <string>
|
|
#include <vector>
|
|
|
|
using namespace std;
|
|
|
|
/**
|
|
* Represents a structure for storing marks records.
|
|
*
|
|
* Attributes:
|
|
* - name : a string representing the name of the student
|
|
* - maths_marks : an integer representing the marks obtained in maths
|
|
* - chinese_marks: an integer representing the marks obtained in chinese
|
|
* - english_marks: an integer representing the marks obtained in english
|
|
* - grade : a string representing the grade obtained based on the marks
|
|
*/
|
|
struct MarksRecord {
|
|
string name;
|
|
int maths_marks, chinese_marks, english_marks;
|
|
string grade;
|
|
};
|
|
|
|
vector<MarksRecord> records;
|
|
|
|
/**
|
|
* Calculates the grade based on the average marks obtained in three subjects.
|
|
*
|
|
* @param maths_marks The marks obtained in Maths.
|
|
* @param chinese_marks The marks obtained in Chinese.
|
|
* @param english_marks The marks obtained in English.
|
|
* @return The grade based on the average marks.
|
|
* - "A" if the average marks are greater than 90.
|
|
* - "B" if the average marks are greater than 80.
|
|
* - "C" if the average marks are greater than 70.
|
|
* - "D" otherwise.
|
|
*/
|
|
string functionGetGrade(int maths_marks, int chinese_marks, int english_marks){
|
|
string grade;
|
|
int marks_sum;
|
|
float marks_avg;
|
|
|
|
marks_sum = 1;
|
|
marks_sum = (maths_marks + chinese_marks + english_marks);
|
|
marks_avg = marks_sum / 3;
|
|
|
|
if (marks_avg > 90) return "A";
|
|
if (marks_avg > 80) return "B";
|
|
if (marks_avg > 70) return "C";
|
|
return "D";
|
|
}
|
|
|
|
/**
|
|
* Displays the menu options for the Mark Record System.
|
|
*
|
|
* The menu options include:
|
|
* 1. Add marks record
|
|
* 2. Delete marks record
|
|
* 3. Edit marks record
|
|
* 4. Print current marks record in system
|
|
* 5. Import records from file
|
|
* 6. Export records to file
|
|
* E. Exit
|
|
*
|
|
* The user is prompted to enter their choice after the menu is displayed.
|
|
*/
|
|
void print_menu() {
|
|
cout << "\n";
|
|
cout << "Mark Record System\n";
|
|
cout << "\n";
|
|
cout << "------------------------------------------\n";
|
|
cout << "1. Add marks record \n";
|
|
cout << "2. Delete marks record \n";
|
|
cout << "3. Edit marks record \n";
|
|
cout << "4. Print current marks record in system \n";
|
|
cout << "5. import records from file \n";
|
|
cout << "6. export records to file \n";
|
|
cout << "------------------------------------------\n";
|
|
cout << "E. Exit\n";
|
|
cout << "Enter your choice: ";
|
|
}
|
|
|
|
/**
|
|
* Adds a new marks record to the system.
|
|
*
|
|
* Prompts the user to enter the name, maths marks, chinese marks, and english marks for the new record.
|
|
* Checks if the entered name is already present in the records. If so, displays an error message.
|
|
* Checks if the entered name is empty. If so, displays an error message.
|
|
* If all checks pass, creates a new MarksRecord object with the entered details and adds it to the records vector.
|
|
*
|
|
*/
|
|
void functionAdd() {
|
|
string temp;
|
|
bool name_pass;
|
|
name_pass = false;
|
|
|
|
MarksRecord record;
|
|
|
|
while (!name_pass){
|
|
bool error;
|
|
error = false;
|
|
|
|
cout << "Enter name: ";
|
|
cin >> temp;
|
|
cin.clear();
|
|
|
|
// check if name entered is empty
|
|
if (temp == string()){
|
|
error = true;
|
|
}else if (temp.find(' ') != string::npos){ // check if name contain space
|
|
cout << "ERROR: name cannot contain space" << endl;
|
|
error = true;
|
|
}
|
|
|
|
if (!error) {
|
|
record.name = temp;
|
|
name_pass = true;
|
|
}
|
|
}
|
|
|
|
cout << "Enter maths marks: ";
|
|
cin >> record.maths_marks;
|
|
cout << "Enter chinese marks: ";
|
|
cin >> record.chinese_marks;
|
|
cout << "Enter english marks: ";
|
|
cin >> record.english_marks;
|
|
|
|
records.push_back(record);
|
|
cout << "1 record added.";
|
|
}
|
|
|
|
|
|
/**
|
|
* Deletes a marks record from the system.
|
|
*
|
|
* This function prompts the user to enter the name of the record to be deleted.
|
|
* It then searches for the record in the 'records' vector and removes it if found.
|
|
* If the record is not found, an error message is displayed.
|
|
*
|
|
*/
|
|
void functionDelete() {
|
|
string name;
|
|
bool user_found;
|
|
user_found = false;
|
|
|
|
cout << "Enter name to delete: ";
|
|
cin >> name;
|
|
for (size_t i = 0; i < records.size(); i++) {
|
|
if (records[i].name == name) {
|
|
records.erase(records.begin() + i);
|
|
user_found = true;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (!user_found){
|
|
cout << "ERROR: student record not found";
|
|
}else{
|
|
cout << "1 record deleted.";
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Edit the marks record for a student.
|
|
*
|
|
* This function allows the user to edit the marks record for a student by entering the student's name and the new marks for each subject.
|
|
* The function searches for the student's name in the records vector and updates the marks accordingly.
|
|
* If the user enters "-" for a subject, the marks for that subject will be skipped and not updated.
|
|
*
|
|
*/
|
|
void functionEdit() {
|
|
string name;
|
|
string temp;
|
|
bool user_found;
|
|
user_found = false;
|
|
|
|
cout << "Enter name to edit: ";
|
|
cin >> name;
|
|
for (size_t i = 0; i < records.size(); i++) {
|
|
if (records[i].name == name) {
|
|
user_found = true;
|
|
cout << "Enter new maths marks [- to skip]: ";
|
|
cin >> temp;
|
|
if (temp != "-") {
|
|
records[i].maths_marks = stoi(temp);
|
|
}
|
|
|
|
cout << "Enter new chinese marks [- to skip]: ";
|
|
cin >> temp;
|
|
if (temp != "-") {
|
|
records[i].chinese_marks = stoi(temp);
|
|
}
|
|
|
|
cout << "Enter new english marks [- to skip]: ";
|
|
cin >> temp;
|
|
if (temp != "-") {
|
|
records[i].english_marks = stoi(temp);
|
|
}
|
|
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (!user_found){
|
|
cout << "sorry but no user found to update record";
|
|
}else{
|
|
cout << "1 record updated.";
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Prints the current marks record in the system.
|
|
*
|
|
* This function displays the student records stored in the 'records' vector.
|
|
* It prints the student name, maths marks, chinese marks, english marks, and grade for each record.
|
|
* The grade is calculated using the 'functionGetGrade' function.
|
|
*
|
|
* Note:
|
|
* - The records are printed in a tabular format with appropriate spacing.
|
|
* - The grade is calculated based on the maths marks, chinese marks, and english marks using the 'functionGetGrade' function.
|
|
*/
|
|
void functionPrint() {
|
|
cout << endl;
|
|
cout
|
|
<< setw(10) << setfill(' ') << left << "Name" << setw(10)
|
|
<< setw(10) << setfill(' ') << left << "Maths" << setw(10)
|
|
<< setw(10) << setfill(' ') << left << "Chinese" << setw(10)
|
|
<< setw(10) << setfill(' ') << left << "English" << setw(10)
|
|
<< setw(10) << setfill(' ') << left << "Grade" << setw(10);
|
|
|
|
cout << "" << setw(50) << setfill('-') << "\n";
|
|
cout << "\n";
|
|
|
|
for (const auto& record : records) {
|
|
string calc_grade;
|
|
calc_grade = functionGetGrade(record.maths_marks, record.chinese_marks, record.english_marks);
|
|
|
|
cout
|
|
<< setw(10) << setfill(' ') << left << record.name
|
|
<< setw(10) << setfill(' ') << left << record.maths_marks
|
|
<< setw(10) << setfill(' ') << left << record.chinese_marks
|
|
<< setw(10) << setfill(' ') << left << record.english_marks
|
|
|
|
// append 2 chars on the left
|
|
<< setw(2) << setfill(' ') << left << " "
|
|
<< setw(10) << setfill(' ') << left << calc_grade << "\n";
|
|
}
|
|
cout << "\n";
|
|
}
|
|
|
|
/**
|
|
* Imports records from a file and adds them to the current marks record system.
|
|
*
|
|
* This function prompts the user to enter the name of a file containing a list of student records.
|
|
* It then opens the file and reads each line, extracting the student name, maths marks, chinese marks, and english marks.
|
|
* A new MarksRecord object is created for each line and added to the records vector.
|
|
* The function keeps track of the number of records added and displays the total at the end.
|
|
*
|
|
* Note:
|
|
* - The file should be formatted with each line containing the student name, maths marks, chinese marks, and english marks separated by spaces.
|
|
* - The last line of the file should contain the word "END" to indicate the end of the records.
|
|
*/
|
|
void functionImport(){
|
|
ifstream inFile;
|
|
ofstream outFile;
|
|
string student_name, maths_mark, chinese_mark, english_mark, grade;
|
|
int record_added;
|
|
record_added = 0;
|
|
|
|
string filename;
|
|
|
|
cout << "Please enter a file with list of student: ";
|
|
cin >> filename;
|
|
|
|
inFile.open(filename);
|
|
if (!inFile) {
|
|
cout << "Cannot open the input file." << endl;
|
|
// << "The program terminates." << endl;
|
|
// return 1;
|
|
}else{
|
|
while (true){
|
|
inFile >> student_name;
|
|
|
|
if (student_name == "END") {
|
|
break;
|
|
}else{
|
|
inFile >> maths_mark >> chinese_mark >> english_mark;
|
|
MarksRecord record;
|
|
record.name = student_name;
|
|
record.maths_marks = stoi(maths_mark);
|
|
record.chinese_marks = stoi(chinese_mark);
|
|
record.english_marks = stoi(english_mark);
|
|
|
|
records.push_back(record);
|
|
|
|
record_added = record_added + 1;
|
|
}
|
|
|
|
}
|
|
|
|
cout << "record imported : " << record_added << "\n";
|
|
cout << "\n";
|
|
|
|
|
|
inFile.close();
|
|
}
|
|
|
|
}
|
|
|
|
/**
|
|
* Exports the student records to a file.
|
|
*
|
|
* This function prompts the user to enter the name of the file to export the records to.
|
|
* It then opens the file and writes the student records in a formatted manner.
|
|
* The file will contain the student name, maths marks, chinese marks, english marks, and grade for each record.
|
|
* The function uses the functionGetGrade() function to calculate the grade based on the marks.
|
|
*
|
|
* Note:
|
|
* - The file will be formatted with each record on a separate line.
|
|
* - The fields will be separated by spaces.
|
|
* - The file will start with a header line indicating the fields.
|
|
* - The file will end with an empty line.
|
|
*/
|
|
void functionExport(){
|
|
ofstream outFile;
|
|
string filename;
|
|
|
|
cout << "Please enter a file to export: ";
|
|
cin >> filename;
|
|
|
|
outFile.open(filename);
|
|
|
|
outFile << setw(10) << setfill(' ') << ""
|
|
<< "~ STUDENT RECORDS ~";
|
|
outFile << "\n";
|
|
outFile << "\n";
|
|
|
|
outFile
|
|
<< setw(10) << setfill(' ') << left << "Name" << setw(10)
|
|
<< setw(10) << setfill(' ') << left << "Maths" << setw(10)
|
|
<< setw(10) << setfill(' ') << left << "Chinese" << setw(10)
|
|
<< setw(10) << setfill(' ') << left << "English" << setw(10)
|
|
<< setw(10) << setfill(' ') << left << "Grade" << setw(10);
|
|
|
|
outFile << "" << setw(50) << setfill('-') << "\n";
|
|
outFile << "\n";
|
|
|
|
for (const auto& record : records) {
|
|
string calc_grade;
|
|
calc_grade = functionGetGrade(record.maths_marks, record.chinese_marks, record.english_marks);
|
|
|
|
outFile
|
|
<< setw(10) << setfill(' ') << left << record.name
|
|
<< setw(10) << setfill(' ') << left << record.maths_marks
|
|
<< setw(10) << setfill(' ') << left << record.chinese_marks
|
|
<< setw(10) << setfill(' ') << left << record.english_marks
|
|
|
|
// append 2 chars on the left
|
|
<< setw(2) << setfill(' ') << left << " "
|
|
<< setw(10) << setfill(' ') << left << calc_grade << "\n";
|
|
}
|
|
outFile << "\n";
|
|
cout << "export done !" << "\n";
|
|
}
|
|
|
|
/**
|
|
* Main function of the program.
|
|
*
|
|
* This function runs a menu-driven program for managing marks records.
|
|
* It continuously displays a menu and prompts the user for their choice.
|
|
* Based on the user's choice, it calls the corresponding functions to perform the desired operation.
|
|
* The program keeps running until the user chooses to exit (e/E).
|
|
*
|
|
*/
|
|
int main() {
|
|
char choice;
|
|
while (true) {
|
|
print_menu();
|
|
cin >> choice;
|
|
|
|
switch (choice) {
|
|
case '1': functionAdd(); break;
|
|
case '2': functionDelete(); break;
|
|
case '3': functionEdit(); break;
|
|
case '4': functionPrint(); break;
|
|
case '5': functionImport(); break;
|
|
case '6': functionExport(); break;
|
|
|
|
// exit handler
|
|
case 'E':
|
|
case 'e':
|
|
return 0;
|
|
|
|
// exception handler
|
|
default:
|
|
cout << "Invalid choice. Please try again.\n";
|
|
}
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|