Reputation: 94
I'm trying to read a file and write the data I read into a structure. With the getline function, i read the whole line, and then divide it in columns. Each term goes into an argument of the structure, and each line is a new instance of the structure. The problem is that my first column is empty.
The folowing code works partially, I read the whole file, all the other columns work perfectly but the first one is filled with nothing.
this is my structure and the data I put into it :
struct employe {
int num_employe;
string nom;
string prenom;
string date_naissance;
string ville_resi;
int code_postal;
};
employe saisir_1_employe(vector<string> row) {
employe e;
e.num_employe = stoi(row[0]);
e.nom = row[1];
e.prenom = row[2];
e.date_naissance = row[3];
e.ville_resi = row[4];
e.code_postal = stoi(row[5]);
return (e);
}
I extract the data from the file like this :
if (myfile.is_open()) {
while (myfile >> temp) {
row.clear();
// read an entire row and
// store it in a string variable 'line'
getline(myfile, line, '\n');
istringstream s(line);
// read every column data of a row and
// store it in a string variable, 'word'
while (getline(s, word, '\t')) {
// add all the column data
// of a row to a vector
row.push_back(word);
}
e = saisir_1_employe(row);
afficher_1_employe(e);
}
}
my file I extract the data from looks like this : https://pastebin.com/Nfhu2tEp
When I display the second column (cout << row[1]
) i get the names perfectly. But when I do cout << row[0]
i get an empty column when it is supposed to be a string that I then convert to an int with e.num_employe = stoi(row[0])
. It's there and has the right number of lines but just empty.
Upvotes: 1
Views: 858
Reputation: 2660
Use getline() by itself to get each line There is no need to use this line:
while(myfile >> temp)
This is grabbing the first word and is never called again.
Instead, loop on each line, by calling getline() on the filestream directly:
while (getline(myfile, line, '\n'))
I like your use of stringstream to parse the words. I probably would have used a stringstream in the saisir function as well to do the parsing calls (e.g. instead of stoi()).
#include <string>
#include <sstream>
#include <iostream>
#include <vector>
#include <fstream>
using namespace std;
struct employe {
int num_employe;
string nom;
string prenom;
string date_naissance;
string ville_resi;
int code_postal;
};
employe saisir_1_employe(vector<string> row )
{
employe e;
e.num_employe = stoi(row[0]);
e.nom = row[1];
e.prenom = row[2];
e.date_naissance = row[3];
e.ville_resi = row[4];
e.code_postal = stoi(row[5]);
return (e);
}
int main()
{
fstream myfile{"myfile.txt"};
std::string line;
std::string word;
std::vector<employe> employees;
if (myfile.is_open()) {
// while (myfile >> temp) {
//
// row.clear();
// read an entire row and
// store it in a string variable 'line'
while (getline(myfile, line, '\n')) {
std::vector<std::string> row;
std::istringstream sline(line);
// read every column data of a row and
// store it in a string variable, 'word'
while (getline(sline, word, '\t')) {
// add all the column data
// of a row to a vector
row.push_back(word);
}
employe e;
e = saisir_1_employe(row);
employees.push_back(e);
// afficher_1_employe(e);
}
int index = 1;
// dump number and nom
for(const auto& emp : employees) {
std::cout << index++ << ". " << emp.num_employe
<< " " << emp.nom << std::endl;
}
}
}
Upvotes: 1
Reputation: 10047
I think you should loop like this
while(std::getline(myfile, line, '\n'))
instead of
while (myfile >> temp)
which is cutting away the first word in every line ...
Upvotes: 2