Read in numbers from console won't stop at newline.

Hello,
I have snippet code from Lippman's <<C++ primer>>.
The program is to convert regular decimal (0 ~ 15) numbers to basic hexdecimals. The instruction tells the program will execute by hitting newline at the end. When I tried to run the compiled program, hitting ENTER did not work as instructed in the book. I have to hit any invalid letter/key or Ctrl+D (I'm using Ubuntu) to terminate the input.

#include <iostream>
#include <string>

using namespace std;

int main ()
{
  const string hexdigits = "0123456789ABCDEF";    //All possible hex digits
  cout << "Enter a series of numbers between 0 and 15"
    << " separated by spaces.\nHit ENTER when finished: " << endl;

  string result;        //will hold the resulting hexify-ed string
  string::size_type n;        //hold numbers from the input

  while (cin >> n)
    if (n < hexdigits.size())    //ignore invalid input
      result += hexdigits[n];    //fetch the individual hex digit

  cout << "Your hex number is: " << result << endl;
  return 0;
}

Exact same question was asked in stackoverflow,

// https://stackoverflow.com/questions/19307979/cin-in-a-while-loop
#include <iostream>
#include <string>
#include <sstream>

using namespace std;

int main ()
{
  const string hexdigits = "0123456789ABCDEF";

  cout <<  "Enter a series of numbers between 0 and 15"
       << " separated by spaces. Hit ENTER when finished: "
       << endl;

  string line;
  string result;

  if (getline (cin, line))    // get the whole line
    {
      istringstream iss(result);    // break them by spaces
      int i;
      while (iss >> i)
    {
      result += hexdigits;
      result += " ";
    }
      cout << "Your hex result:  " << result << endl;
    }
  else
    {
      cout << "Error handling input!" << endl;
    }

  return 0;
}

1) which used getline() and I can't get the logic flow and the posted code did not work as expected; and
2) it seems there may be better way for this basic trick.
My question is what is the best practice to stop reading space-delimited numbers at newline instead of Ctrl+D or by hitting any invalid char?
Thanks!

The >> operator does not care at all about lines. If you want lines, you'll have to separate it some other way, which is exactly what the stackoverflow code does.

It reads entire lines with getline, then crams the entire line into a stringstream object. A stringstream, unlike standard input, will just hit EOF when it runs out of data instead of waiting for more.

2 Likes

Thanks Corona688!
I did not forget your advice on fgets() + sscanf() in C. Switched from there I was hoping to get similar advice in C++ so that I used "best practice". I am aware this is about very basic I/O stream that I'm still struggling with.
Spend more time on this, and found out my confusion also related to this line of the stackoverflow code, which seems wrong to me:

istringstream iss(result);  // break them by spaces, Wrong code!!
istringstream iss(line);    //This gave me what I expected.

My question seems answered.
Thanks again!

1 Like

It's the exact same problem as fgets, too.