tags:

views:

734

answers:

3

Hey folks.

I'm a little confused as to what's going on, i'm playing with some programs from "Accelerated C++", and have hit a problem with one of the early programs (page 35, if you happen to have a copy nearby).

It uses this snippet:

while (cin >> x) {
   ++count;
   sum += x;
}

("count" is an integer, "x" is a double)

It works as intended, allowing me to enter several values and add them together, but i can't work out what's going wrong with "End-of-file" signalling. The book says the loop will keep running until the program encounters an end of file signal, which is ctrl+z in windows.

This is all fine, and works, but then my program won't let me use cin again. I usually just set up a program to wait for some random variable in order to stop the console closing immediately after executing (is there a better way to do that, by the way?) which is how i noticed this, and i'm wondering if there's a solution. I've done a bunch of searching, but found little that doesn't say what's already said in the book (press ctrl+z, or enter a non-compatible type of input etc.)

I'm using Visual studio 2008 express to compile.

+2  A: 

EOF means that STDIN (otherwise known as cin) has been closed. Closed means it can't be used again.

That said, I think it's possible to open another stream to the input, but the better, and more normal solution is to do better input/output processing, and allow your user to input some token that says 'stop accepting input'.

Matthew Scharley
+6  A: 

From one point of view, once you've hit the end of an input stream then by definition there's nothing left in the stream so trying to read again from it doesn't make sense.

However, in the case of 'end-of-stream' actually being caused be a special character like Ctrl-Z on windows, we know that there is the possibility that we could read again from cin. However, the failed read will have caused the eof flag on the stream to be set.

To clear this flag (and all the other failure flags) you can use the clear method.

std::cin.clear();

After calling this, you can attempt another read.

Charles Bailey
Perfect, thank you kindly.
Dmatig
And in the case it actually IS the end of input (think piped input)
Matthew Scharley
It depends on the implementation, in many scenarios a piped read will just block until there is something to read rather than setting the fail/eof bits on the stream.
Charles Bailey
+1  A: 

It looks like you are using windows (otherwise you would be on the console and the window would not close). You have two options.

  • Run the application from the command line:
    • Start cmd. cd to the correct directory. Then execute the command.
      Output is done correctly to the console and the windows does not close.
  • Use another method to stop the window closing
    • Easiest way is Pause.
      system("Pause")
  • If you don't end the input stream you can reset it.
    • ie. If you type some text that causes the operator>> to fail the error bit is set.
      You can reset the error bit with cin.clear()
      This probably will not work if you close the stream with ctrl-Z
  • Note if you try and use cin >> pause; (where pause is char or something)
    Make sure the stream is empty by using cin.ignore() otherwise the pause will not happen
    as the code will just continue after reading the data
Martin York