简体   繁体   中英

file i/o infinite loop c++ eof

I have started working on a program, and for the life of me I can't find a bug which continuously searches the eof and doesn't end. It is most certainly a problem with my fileread and widthcount functions, and they most likely have the same error. Is there a fix for this? It just keeps looping.

The file input is this

12.43 62.38 Los Angeles
21 59 Columbus, Ohio
0 15.58 Green Bay, Wisconsin

This continues for another 10 lines.

#include <iostream>
#include <fstream>
#include <cstdlib>
#include <iomanip>
using namespace std;

void fileread(ifstream &ifFile, char newline, double &temp1, double &temp2, string city);
void widthcount(ifstream &ifFile, int &maxCount, char newline);

int main() {
   double temp1, temp2, minTemp, maxTemp;
   int maxCount;
   char newline=' ';
   string FileRead, city;
   ifstream ifFile;

   cout << "Please enter the location of the input file: ";
   cin >> FileRead;

   ifFile.open(FileRead.c_str());

   if (ifFile.fail()) {
       perror(FileRead.c_str());
       exit(1);
   }

   widthcount(ifFile, maxCount, newline);

   while(!ifFile.eof()) {
       widthcount(ifFile, maxCount, newline);
   }      

   ifFile.close();

   ifFile.open(FileRead.c_str());

   fileread(ifFile, newline, temp1, temp2, city);

   while(!ifFile.eof()) {
       fileread(ifFile, newline, temp1, temp2, city);

       cout << left << setw(20) << city
             << right << setw(6) << fixed << setprecision(2) << temp1
             << right << setw(6) << fixed << setprecision(2) << temp2 << endl;

   }

}

void fileread(ifstream &ifFile, char newline, double &temp1, double &temp2, string city) {
   int charcount = 0;

   ifFile >> temp1 >> temp2;

   while (newline == ' ')
       ifFile.get(newline);
   while (newline != '\n' || !ifFile.eof()) {
       charcount++;
       ifFile.get(newline);
   }
}

void widthcount (ifstream &ifFile, int &maxCount, char newline) {
   double temp1, temp2;
   int charcount = 0;
   ifFile >> temp1 >> temp2;
   ifFile.get(newline);
   while (newline != '\n' && !ifFile.eof()) {
       charcount++;
       ifFile.get(newline);
       cout << newline;
   }

   if (charcount > maxCount)
    maxCount = charcount;
}

You need to check for failure (test .fail() ), not end of file.

Typically .fail() is checked by using the stream object directly as condition.

Eg while( f ) is equivalent to while( !f.fail() ) .

Checking specifically for eof() is almost always a mistake -- for example, if you encounter some other error before reaching the end of the file, eof will remain false, but reading will fail (but since eof remains false, your loop will continue attempting to read and failing, forever).

Personally, I'd structure the code quite a bit differently. I'd start by creating a struct to represent one "record" from the file:

struct city {
    double temp1, temp2; // horrible names, but I don't know what they represent.
    std::string name;
};

Then I'd overload operator>> to extract the data for one city from a stream, and operator<< to display the data for a city:

std::istream &operator>>(std::istream &is, city &c) { 
    is >> c.temp1 >> c.temp2;
    std::getline(is, c.name);
    return is;
}

std::ostream &operator<<(std::ostream &os, city const &c) { 
    return cout << left << setw(20) << c.name
                << right << setw(6) << fixed << setprecision(2) << c.temp1
                << right << setw(6) << fixed << setprecision(2) << c.temp2;
}

Then I'd use those to read and write the data as god intended (with an algorithm):

int main(int argc, char **argv) {

    // For the moment, cheat and take the file name from the command line
    std::ifstream ifFile(argv[1]);

    std::copy(std::istream_iterator<city>(ifFile),
              std::istream_iterator<city>(),
              std::ostream_iterator<city>(std::cout, "\n"));
    return 0;
}

As an aside, I'd note that although you call widthcount , you never seem to use any result from it. At least for now, I've skipped over doing anything similar, since it didn't affect the result.

You should try something like

double t1,t2;
string s1,s2;

ifstream ifs;
ifs.open(Filename.c_str());

ifs>>t1>>t2>>s1>>s2;

while(ifs)
{
.......
do the calculations
.......
ifs>>t1>>t2>>s1>>s2;
}

This works for all the cases.If ,after the first read, ifs enters the fail state then rest of the file reading will be skipped and lines after the while loop will be executed.Other wise, rest of the lines will be read in the loop.You can change your requirement based on whether you want to read a string,a character or a line.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM