Handling end-of-file (eof) correctly                   (Carol Zander, CSS 343)
------------------------------------

The eof() function, as in   infile.eof()  , is a bool function which is
true if the EOF character has been read, false otherwise. When you have
read the last item in a file, the eof function may not be true yet.
Often you have to read past the last item in the file to read the
EOF character so the eof function will be true.


Unix/Linux vs. Windows
----------------------

On unix/linux, every line in a file has an End-Of-Line (EOL) character and
the EOF character is after the last line. On windows, each line has an EOL
characters except possibly the last line. So unix/linux file's last line is
      stuff, EOL, EOF
whereas windows file's last line, if the cursor is on the line, is
      stuff, EOF

So set up data files on windows to be the same as on unix/linux. This way,
you will correctly determine eof under both unix/linux and windows.
To do this, make sure the cursor is on the line after the last line of data.

In general, you must exit all loops and all functions immediately when you
are attempting to read an item that would be past the eof.

Here is a typical set up that will work correctly. Suppose in a data file,
there are multiple lines of data. In some function is the loop where you are
reading and handling this data. This loop will look similar to the following. 

     // infinite loop to read and handle data
     for (;;) {                 // or use:  while (true)
        infile >> data;
        if (infile.eof()) break;

        // do whatever with data
     }

If you dislike infinite loops, you can accomplish this same thing using a while
loop by priming the loop and reading again at the end. But with some problems 
this code can get complex, so I recommend getting used to the infinite loop.

     infile >> firstThingOnTheLine;
     while (!infile.eof()) {
        // read the rest of the line
        // do whatever with data

        infile >> firstThingOnTheLine;
     }

You MUST do it one of these ways. Do not adjust your code.
Adjust the data file to work with this code. 

Often reading is done in a routine.  In that case, exit both.
This loop is similar to that situation.

     for (;;) {
        obj.setdata(infile);      // method does reading
        if (infile.eof()) break;

        // do whatever with obj
     }

void ObjClass::setdata(istream& infile) {
     infile >> data;              // read first item so EOF char is read
     if (infile.eof()) return;    // determine no more data

     // probably read more data to fill rest of object
}

