Vector "out of range" error in a simple program storing words inputted into a vector

I am trying to store user input all words a user inputs into a vector, with each word being an element. The user can input as many lines of words as he wants, and when finished, uses CTRL+D to specify end of file. A word is any characters separated by a comma or space. The following code compiles but I get this error:

Error: terminate called after throwing an instance of 'std::out_of_range'
what(): vector::_M_range_check: __n (which is 1) >= this->size() (which is 1)

My code:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
#include <vector>
#include <string>
#include <sstream>
#include <iostream>

using namespace std;

int main(){

    string input;
    vector<string> hand;
    istringstream sso;

    cout << "Enter your string: " << endl;

    while (cin >> input){
        
        sso.str(input);
    
        while(getline(sso, input, ',')) {

            hand.push_back(input);
        
        }

    }

    cout << hand.at(0) << endl;
    cout << hand.at(1) << endl;
    cout << hand.at(2) << endl;

    return 0;

}


Any help is appreciated. Thank you.
Last edited on
You aren't clearing the flags on your istringstream, meaning that you are only adding one object to your vector. This means that when you try to do hand.at(1) you are accessing an element that doesn't exist, hence your program throwing an exception.

To fix it, either add sso.clear() at the end of the loop, or just declare your variables inside the loop:
1
2
3
4
5
6
7
8
9
10
11
12
std::string input;
std::cout << "Enter your string:\n";
while (std::cin >> input) {
    std::istringstream iss(input);
    while (std::getline(iss, input, ',')) {
        hand.push_back(input);
    }
}

// print contents of vector
for (const auto& str : hand)
    std::cout << str << std::endl;
That did it, thank you. One more quick question--I'm trying to add a vector containing 52 strings but I am getting many errors (new to vectors). Here's what I have:

vector <string> cards{"2C", "3C", "more cards", "2S"}; //etc.

I will post exact errors if needed but I figured this is a noobie mistake that is easy to solve (it's like 2 pages worth of errors).

Thank you.

What you have there is correct. Could you post more of your program?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
#include <vector>
#include <string>
#include <sstream>
#include <iostream>

using namespace std;

int main(){


    string input;
    vector <string> hand;
    vector <string> cards{"2C", "3C", "4C", "5C", "6C", "7C", "8C", "9C", "10C", "JC", "QC", "KC", "AC",
                          "2D", "3D", "4D", "5D", "6D", "7D", "8D", "9D", "10D", "JD", "QD", "KD", "AD",  
                          "2H", "3H", "4H", "5H", "6H", "7H", "8H", "9H", "10H", "JH", "QH", "KH", "AH",
                          "2S", "3S", "4S", "5S", "6S", "7S", "8S", "9S", "10S", "JS", "QS", "KS", "AS"};

    istringstream sso;

    cout << "Enter your string: " << endl;

    while (cin >> input){
        
        sso.str(input);
    
        while(getline(sso, input, ',')) {

            hand.push_back(input);

        }

        sso.clear(); 
        

    }

    cout << hand.at(0) << endl;
    cout << hand.at(1) << endl;
    cout << hand.at(2) << endl;

    return 0;

}



P.S. 2 more small questions if you don't mind:

1. I used istringstream's behavior to separate words by whitespace and then `getline(sso, input, ','))` to separate words by commas. How can I add in separating words by newlines? I don't think getline allows more parameters to be set and the 3rd one is used by the comma. Would `getline(sso, input, ',')) || getline(sso, input, '\n'))` work?


2. (This one is just out of curiosity) If I use the program and typed "hello i am a cat" then typed "CTRL+D" to initiate end-of-file to finish the input without clicking ENTER, it returns "hello i am" as expected but like this:

"hello i am cathello
i
am"

Is there an "endl" equivalent for that so it looks pretty?
Last edited on
Aren't you slighly double-posting. First thread: http://www.cplusplus.com/forum/beginner/184545/

The order of operations could make a difference:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
#include <iostream>
#include <iomanip>
#include <string>
#include <sstream>
#include <vector>

void separator() {
  std::cout << std::setfill('#') << std::setw(10) << '\n';
}

int main ()
{
  std::vector<char> types { 'x', 'y', 'z' };
  std::string Q("Q");
  std::vector<std::string> foo;
  foo.reserve(12);
  for ( auto t : types ) {
      for ( int w = 4; w < 7; ++w ) {
          foo.push_back( t + std::to_string(w) );
      }
      foo.push_back( Q+t );
  }
  std::cout << "foo has:\n";
  for ( auto word : foo ) {
      std::cout << ' ' << word;
  }
  std::cout << "\n\n";

  std::ostringstream data( "A B,C \nD\n,,E" );

  std::cout << "The user would type:\n";
  separator();
  std::cout << data.str() << '\n';
  separator();

  std::istringstream ins( data.str() );
  
  std::string text;
  std::string line;
  while ( std::getline( ins, line ) ) {
      text += ' ' + line;
  }
  std::cout << "\nThe program did read:\n";
  separator();
  std::cout << text << '\n';
  separator();
  // How could one replace characters, like commas, in a string?
  
  // If you have a string with only whitespace and words ...
  return 0;
}

Lines 40-42 and following comments might give you an idea.


Lines 13-22 are more lines than your lines 13-16 vector initializer, but less tedious to write.
Topic archived. No new replies allowed.