Question

I'm running myself through a C++ text book that I have as a refresher to C++ programming. One of the practice problems (without going into too much detail) wants me to define a function that can be passed ifstream or cin (e.g. istream) as an argument. From there, I have to read through the stream. Trouble is, I can't figure out a way to have this one function use cin and ifstream to effectively find the end of the stream. Namely,

while(input_stream.peek() != EOF)

isn't going to work for cin. I could rework the function to look for a certain phrase (like "#End of Stream#" or something), but I think this is a bad idea if the file stream I pass has this exact phrase.

I have thought to use function overloading, but so far the book has mentioned when it wants me to do this. I'm probably putting too much effort into this one practice problem, but I enjoy the creative process and am curious if there's such a way to do this without overloading.

Was it helpful?

Solution

eof() does work for cin. You are doing something wrong; please post your code. One common stumbling block is that eof flag gets set after you try to read behind the end of stream.

Here is a demonstration:

#include <iostream>
#include <string>

int main( int, char*[] )
{
    std::string s;
    for ( unsigned n = 0; n < 5; ++n )
    {
        bool before = std::cin.eof();
        std::cin >> s;
        bool after = std::cin.eof();
        std::cout << int(before) << " " << int(after) << "  " << s << std::endl;
    }

    return 0;
}

and its output:

D:>t
aaaaa
0 0  aaaaa
bbbbb
0 0  bbbbb
^Z
0 1  bbbbb
1 1  bbbbb
1 1  bbbbb

(EOF can be generated with Ctrl-Z on Windows and Ctrl-D on many other OSes)

OTHER TIPS

Why won't std::cin.eof() work? cin will signal EOF when stdin closes, which will happen when the user signals it with Ctrl+d (*nix) or Ctrl+z (Windows), or (in the case of a piped input stream) when the piped file ends

If you use a stream in a boolean context then it will convert itself into a value that is equivalent to true if it has not reached the EOF and false if an attempt has been made to read past the EOF (not it is also false if there was a previous error reading from the stream).

Since most IO operations on streams return the stream (so they can be chained). You can do your read operation and use the result in the test (as above).

So a program to read a stream of numbers from a stream:

int main()
{
   int x;

   // Here we try and read a number from the stream.
   // If this fails (because of EOF or other error) an internal flag is set.
   // The stream is returned as the result of operator>>
   // So the stream is then being used in the boolean context of the while()
   // So it will be converted to true if operator>>  worked correctly.
   //                         or false if operator>> failed because of EOF
   while(std::cin >> x)
   {
       // The loop is only entered if operator>> worked correctly.
       std::cout << "Value: " << x << "\n";
   }

   // Exit when EOF (or other error).
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top