Чтение всех данных из файла - PullRequest
0 голосов
/ 13 мая 2019

Я пишу программу для отображения отчета об оценке учеников из текстового файла. У меня проблема с правильным перечислением курсов для студента, потому что первый курс пропускается и заменяется первой строкой из следующей строки в файле. Я также могу отображать результаты только для одного ученика в файле вместо всех учеников.

Я не уверен, как обратиться к пропущенному курсу в данных. Я попытался настроить начальный цикл несколькими различными способами, но я либо получаю результат, который у меня есть, либо непрерывный цикл только с одним учеником

#include <iostream>
#include <string>
#include <fstream>

using namespace std;

int main() {

    string ID, lastName, firstName;
    char midInt, sex, letterGrade;
    string phoneNum, classLevel, courseName;
    int regCourses, courseCredit;
    double numGrade, totalNumGrade;
    int credits2018, credits2019;
    double cumGPA2018, cumGPA2019;
    int i;
    ofstream out_stream;
    ifstream in_stream;

    in_stream.open("C:/Users/mss3s_000/Desktop/Stud.txt");

    if (in_stream.fail()) {
        cout << "Input file opening fail.\n";
        exit(1);
    }


    if (!in_stream.eof()) { //I think the issue with not reading all the data is with this loop, but I'm not sure.
        while (in_stream >> ID >> lastName >> firstName >> midInt >> phoneNum >> sex >> classLevel >> credits2018 >> cumGPA2018 >> regCourses >> courseName >> courseCredit >> letterGrade) {

             switch (sex) {
                case 'M':
                    /*sex = "Male";*/
                    break;
                case 'F':
                    /*sex = "Female";*/
                    break;
            }

            if (classLevel == "FR")
                classLevel = "Freshman";
            else if (classLevel == "SO")
                classLevel = "Sophomore";
            else if (classLevel == "JR")
                classLevel = "Junior";
            else if (classLevel == "SR")
                classLevel = "Senior";

            if(letterGrade == 'A')
                numGrade = 4.0;
            else if(letterGrade == 'B')
                numGrade = 3.0;
            else if(letterGrade == 'C')
                numGrade = 2.0;
            else if(letterGrade == 'D')
                numGrade = 1.0;
            else if(letterGrade == 'F')
                numGrade = 0.0;

            cout << "**************************************************" << endl;
            cout << "Student ID number: " << ID << endl;
            cout << "Name: " << lastName << ", " << firstName << " " << midInt << endl;
            cout << "Tel: " << phoneNum << endl;
            cout << "Gender: " << sex << endl;
            cout << "Class Level: " << classLevel << endl;


            if (regCourses == 0) {
                cout << "Registration of Spring 2019: " << "No" << endl;
                cout << "**************************************************" << endl;


            }

            cout << "Registration of Spring 2019: " << "Yes" << endl;
            cout << "\n Unofficial Report Card" << endl;
            cout << "COURSE     CREDITS      GRADE" << endl;
            cout << "======     =======     ======" << endl;
            credits2019 = 0;
            cumGPA2019 = 0.0;

            for (i = 1; i <= regCourses; i++) { //I thought this loop would show all the courses but it is skipping the first course
                in_stream >> courseName;
                in_stream >> courseCredit;
                in_stream >> letterGrade;


                if (letterGrade != 'W') {
                    credits2019 += courseCredit;
                    totalNumGrade += (courseCredit * numGrade);
                    cumGPA2019 = totalNumGrade / credits2019;
                }
                cout << courseName << " " << courseCredit << " " << letterGrade << endl;
                out_stream << courseName << " " << courseCredit << " " << letterGrade << endl;
            }

            cout.setf(ios::fixed);
            cout.setf(ios::showpoint);
            cout.precision(2);
            cout << "\nCredits for Spring 2019: " << credits2019 << endl;
            cout << "GPA till Fall 2018: " << cumGPA2018 << endl;
            cout << "Total Credits: " << (credits2018 + credits2019) << endl;
            cout << "New Cumulative GPA: " << ((credits2019 * cumGPA2019) + (credits2018*cumGPA2018)) / (credits2019 + credits2018) << endl;
            cout << "**************************************************\n" << endl;

        }
    }
    in_stream.close();


    return 0;
}

Я ожидал, что все классы будут перечислены под заголовком курса и отобразят информацию для всех студентов в файле.

1 Ответ

0 голосов
/ 13 мая 2019

Вы можете прочитать файл построчно, используя getline() и проверить возвращаемое значение, чтобы узнать, достиг ли вы конца файла или нет.

Я сделал простой пример, который читает все данныеиз файла и загрузите их в «список студентов».

Вот как вы можете это сделать:

файл данных

name:Bob
sex:Male
age:18
name:Alice
sex:female
age:16

код C ++

#include <iostream>
#include <fstream>
#include <vector>

struct Student
{
    std::string name;
    std::string sex;
    std::string age;

    void clear()
    {
        name.clear();
        sex.clear();
        age.clear();
    }
};

std::pair <std::string, std::string> breakdown(const std::string & line);

int main()
{
    std::string data_file("../tmp_test/data.txt");
    std::vector <Student> students;

    std::ifstream in_s(data_file);
    if(in_s)
    {
        std::string line;
        Student current;
        while(getline(in_s, line))
        {
            std::pair <std::string, std::string> pair = breakdown(line);
            if(pair.first == "name") // first field
            {
                current.name = pair.second;
            }
            else if(pair.first == "sex")
            {
                current.age = pair.second;
            }
            else if(pair.first == "age") // last field
            {
                current.sex = pair.second;
                students.push_back(current);
                current.clear(); // Not necessary
            }
            else
                std::cout << "Info: Unknown field encountered !" << std::endl;
        }

        in_s.close();
    }
    else
        std::cout << ("Error: Could not open file: " + data_file) << std::endl;

    // Do what you want with the loaded data
    for(Student s : students)
    {
        std::cout << "Name: " << s.name << "\nSex: " << s.sex << "\nAge: " << s.age << "\n";
        std::cout << std::endl;
    }

    return 0;
}

std::pair <std::string, std::string> breakdown(const std::string & line)
{
    bool found(false);
    unsigned int i;
    for(i = 0; !found && (i < line.length()); ++i)
    {
        if(line[i] == ':')
        {
            found = true;
            --i;
        }
    }
    if(found)
        return std::make_pair<std::string, std::string>(line.substr(0, i), line.substr(i+1, line.size()-i));
    else
        return std::make_pair<std::string, std::string>("", "");
}

выход

Имя: БобПол: 18Возраст: мужской

Имя: АлисаПол: 16Возраст: женщина

Это хорошо сработало для меня.Конечно, я не справился, если файл данных поврежден, но дело не в этом.Я попытался сделать это как можно проще, просто чтобы показать, как это можно сделать.

Надеюсь, это поможет.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...