Ifstream does not read the EOF character

I am creating a program (in C ++) that takes an ASCII file and reads several values ​​from each line until it reaches the end of the file. I use ifstream to read a file and I never had a problem stopping it when I use the ifstream.eof() method. However, this time, although he found the eof character in my test case, when I parsed my other files, this is an endless loop because it never finds the eof character. Is this a problem with the encoding or a problem with my files?

 string line = ""; unsigned long pos = 0; ifstream curfile(input.c_str()); getline(curfile, line); int linenumber = 0; cout<<"About to try to read the file"<<endl; if (!curfile.good()) cout<<"Bad file read"<<endl; while (!curfile.eof()) { cout<<"Getting line "<<linenumber<<endl; linenumber++; pos = line.find_first_of(' '); line = line.substr(pos+1, line.size()-1); pos = line.find_first_of(' '); current.push_back(atof(line.substr(0, pos).c_str())); for (int i = 0; i<4; i++) { pos = line.find_first_of(' '); line = line.substr(pos+1, line.size()-1); } pos = line.find_first_of(' '); dx.push_back(atof(line.substr(0, pos).c_str())); pos = line.find_first_of(' '); line = line.substr(pos+1, line.size()-1); pos = line.find_first_of(' '); dy.push_back(atof(line.substr(0, pos).c_str())); getline(curfile, line); } 

EDIT: When I first run the loop, currentfile.good () returns false ... what am I doing that causes it to return this?

+1
c ++ eof ifstream
source share
4 answers

First of all, you should not check like that. eof() does not return true until after it is read. But you can do better (and easier)!

check the state of a stream with an implicit conversion to void* , which can be used in a bool context . Since most read operations in streams return a reference to the stream, you can write very consensus code as follows:

 std::string line; while(std::getline(currentfile, line)) { // process line } 

Basically, what he does is say, "while I was able to successfully extract the string from the currentfile , do the following", which you really wanted to say anyway; -);

As I said, this applies to most stream operations, so you can do things like this:

 int x; std::string y; if(std::cin >> x >> y) { // successfully read an integer and a string from cin! } 

EDIT . I would rewrite your code like this:

 string line; unsigned long pos = 0; int linenumber = 0; ifstream curfile(input.c_str()); std::cout << "About to try to read the file" << std::endl; while (std::getline(curfile, line)) { std::cout << "Getting line " << linenumber << std::endl; linenumber++; // do the rest of the work with line } 
+4
source share

Do not do it like this.

EOF is not the only thing you will encounter while reading. There are a bunch of bugs there, and it’s best to just test the stream itself:

 while(currentfile) { // read somehow } 

If you are reading the lines, then the easiest way:

 std::string line; while(std::getline(currentfile, line)) { // use line } 
+2
source share

Your first getline call fires one of the crash bits in the ifstream object. Therefore, if you perform a failure check using ios::good() , you never enter your read loop. I would see what the value of line ... it is probably empty, which means that you have another problem reading your file, for example, permission problems, etc.

+2
source share

The problem is here:

 if (!curfile.good()) cout<<"Bad file read"<<endl; // OK you print bad. while (!curfile.eof()) // But the loop is still entered. // Another reason to **NEVER** to use // while (file.eof()) // as bad does not mean eof // though eof is bad 

Try the following:

 void readFile(std::istream& str) { std::string line; while(std::getline(str, line)) { std::stringstream lineStream(line); std::string ignoreWord; int number[3]; lineStream >> ignoreWord // reads one space seporated word >> number[0] // reads a number >> ignoreWord >> ignoreWord >> ignoreWords // reads three words >> number[1] // reads a number >> number[2]; // reads a number current.push_back(number[0]); dx.push_back(number[1]); dy.push_back(number[2]); } } 
+1
source share

All Articles