2

For the input,

1
4 2
1 2
1 3
1

The Program,

#include <cmath>
#include <cstdio>
#include <vector>
#include <iostream>
#include <algorithm>
using namespace std;


int main() 
{
  int Q;
  cin >> Q;   //Q=2

  while(Q--)
  {
    int N, E;
    cin >> N >> E;  // N=4, E=2    

    while(1)
    {
      string edge;
      getline(cin,edge); //edge should store "1 2" for the first iteration and "1 3" for the second iteration.
      cout << edge << " " << edge.size() << endl;
      vector<int> adjList[N];

      if(edge.size()>1)
      {
        int u = stoi(edge.substr(0,1));
        int v = stoi(edge.substr(2,1));

        for(int i=0; i<E; ++i)
        {
          adjList[u].push_back(v);
          adjList[v].push_back(u);
        }
      }

      else
        break;
    }
  }

  return 0;
}

gives output

0

The program should print out,

1 2 3
1 3 3
1 1

Why am I not storing any value in the string edge? I think it's the getline() function which causes the problem. Are there other functions that can take the whole line as into a string (including spaces) until a newline is reached?

Jonathan Wakely
  • 166,810
  • 27
  • 341
  • 521
  • If you're intending to work in idiomatic C++ you should avoid C Standard Library headers (namely `cstdio`). As you're already using C+'s `` there isn't much of a need for `cstdio`. – Dai Feb 15 '17 at 02:56

1 Answers1

1

After executing this statement:

cin >> N >> E;  // N=4, E=2

the next thing in the input stream is a newline character, which isn't consumed by reading an int into E. So the first call to getline(cin, edge) just reads up to that newline character, which is an empty string.

You need to read more data from the stream so that the first call to getline reads a new line, not whatever is left after reading N and E.

You can do that like this:

cin >> N >> E;  // N=4, E=2
string dummy;
getline(cin, dummy);  // read rest of line

This will read up to a newline into a dummy variable, so the next read starts on the next line.

Or like this:

cin >> N >> E;  // N=4, E=2
cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');

This will tell the cin stream to discard characters until either:

  • it has read std::numeric_limits<std::streamsize>::max() characters (which is a very very large number), or
  • it reads a \n character (i.e. the next newline character).

Again, this means the next read will start on the next line.

Since you know that there's no whitespace or other data between the value read into E and the newline, you don't need to discard a very very large number of characters and you could actually make it simpler:

cin >> N >> E;  // N=4, E=2
cin.ignore(20, '\n');

This will just discard a maximum of 20 characters, or the next newline, whichever comes first.

If you're absolutely sure there's nothing at all before the newline, you can just ignore a single character:

cin >> N >> E;  // N=4, E=2
cin.ignore();  // discard a single character

This should work for your case, but is a bit more fragile because if somebody inserts a space into your input file things will stop working again.

Jonathan Wakely
  • 166,810
  • 27
  • 341
  • 521