3

I'm working on homework for my c++ class, and it's been quite awhile since I've used it. I was wondering if there was a way to allow spaces in a string (instead of it nulling out and ending the string) my current code is this:

int chapter10() {

    string strinput;
    char charstr[1000];
    int numwords=1;

    cout << "Enter a phrase ";
    cin >> strinput;
    cout << strinput;
    const int size = strinput.size() + 1;

    strcpy_s(charstr, strinput.c_str());

    cout << strinput << endl;

    for (int i = 0; i != size; i++) {
        if (*(charstr + i) == ' ')
            numwords++;
    }

    cout << "There are " << numwords << " words in that string." << endl;
    return 0;
}

The problem I'm having, is for instance, if I type "Hello World" and press enter, it pops the next line (right after the cin) and says "Hello", and the space made it cut the rest of the phrase off.

How does one fix this issue? I don't want to use the str:: things as I barely know what they are, and have really never had to use them, and that would look a bit suspicious to the teacher :P

Update: If you've suggested using getline(cin, strinput); It doesn't work too well. I can from what I see, only type in the 10 to reach my function, but after I press enter, it thinks that I've presses something else, which makes it completely skip the cin to get the string value. But, there is something weird with this, if I type "10 hello world" it does everything correctly. Well, with the exception that it needs to be in the same line as the number to reach the function.

Solved: The use of getline(cin, strinput) works perfectly fine, if you're not using user input before hand. If you are, you're going to need a cin.ignore before the getline(). As stated in the comment by my best answer.

#include <iostream>
#include <iomanip>
#include <string>
#include <limits>

using namespace std;

//~~~Initialize all functions
int chapter10();
//~~~Initializing complete

int main() {
    srand(time(0)); //makes rng thingy work instead of choose same numbers cause it doesn't do it on its own. lol
    cout << "Enter the chapter number you need to look at: ";
    int chapterNumber;
    cin >> chapterNumber;

    switch (chapterNumber) {
    case 1: testingStuff(); break;
    case 9: chapter9(); break;
    case 10: chapter10(); break;
    default: cout << "You chose an invalid chapter number, reload the program."; break;
    }

    system("pause");//So console doesn't close instantly cause that's not annoying at all...

}

int chapter10() {

    string strinput;
    char charstr[10000];
    int numwords=1;

    cout << "Enter a phrase." << endl;

    cin.ignore(numeric_limits<streamsize>::max(), '\n');
    getline(cin, strinput);                             
    const int size = strinput.size() + 1;

    strcpy_s(charstr, strinput.c_str());

    for (int i = 0; i != size; i++) {
        if (*(charstr + i) == ' ' & *(charstr + (i+1)) != ' ' )//the & is fail safe so multiple space no ++numwords
            numwords++;
    }

    cout << "There are " << numwords << " words in that string." << endl;
    return 0;
}

The way I have my code written was I used a switch/case to reach my function. This required user input, which in turn caused my program to 'think' I was still typing for the second input required in the chapter10 function.

Adding in the line of code: cin.ignore(numeric_limits<streamsize>::max(), '\n'); allowed me to cancel the input, and start a new one.

John Olivas
  • 309
  • 1
  • 2
  • 14

4 Answers4

3

If you want to get all characters an end-user enters on a single line, use getline: instead of cin >> strinput write this:

getline(cin, strinput);

The fact that it is actually std::getline(std::cin, strinput) makes no difference, because your code uses std namespace anyway. In case you were wondering what std:: prefix is, it's a namespace of the Standard C++ library.

Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523
  • Okay, finally got it to stop giving me compiler errors (not really sure what I did) but now it is just skipping the part where it lets you enter something, http://prntscr.com/9rw755 I type in 10, and it instantly finishes, and doesn't let me enter my string. This picture: http://prntscr.com/9rw847 is because trying to type code in a comment doesn't work very well – John Olivas Jan 19 '16 at 00:16
  • 1
    @JohnOlivas You probably call your function after some other function that performs user input. In that case you need to ignore `'\n'` remaining in the input buffer. Add this line before `getline`: `cin.ignore(numeric_limits::max(), '\n');`, and add `#include ` at the top of your program. – Sergey Kalinichenko Jan 19 '16 at 00:31
2

You can use getline() function
It copies into a string till a newline is reached or delimiter is found - so it will accept all the spaces till newline is reached http://www.cplusplus.com/reference/string/string/getline/

or you can also use cin.getline() as shown here -
std::cin input with spaces?

Community
  • 1
  • 1
novice
  • 545
  • 3
  • 16
  • Ok, so I used this as well, comes up with same problem, I enter my case statement to get to my function, when I press enter after the chapter number (how I get there) it skips the entire cin line, I don't press anything after typing "10" and it just skips it. BUT if I type "10 hello world" it grabs the string hello world, and does what its supposed to... just, not at the right time. – John Olivas Jan 19 '16 at 00:26
  • string c; std::getline(cin,c); cout< – novice Jan 19 '16 at 00:37
  • dasblink fixed it for me, because I was using my main function for userinput to reach the function this program is in, it was still using what I entered as the user input. – John Olivas Jan 19 '16 at 00:40
1

use:

cin >> noskipws >> strinput;
EDD
  • 2,070
  • 1
  • 10
  • 23
1

Use std::getline() function. Example:

#include <iostream>
#include <vector>
#include <sstream>

void WordCounter(
    const std::vector<std::string> & lines) {
  for (int i = 0; i < lines.size(); ++i) {
    std::istringstream iss(lines[i]);
    std::string word;
    int count = 0;
    while (iss >> word) {
      ++count;
    }
    std::cout << "Line #" << i << " contains " << count << " words." <<
        std::endl;
  }
}

int main() {
  std::string line;
  std::vector<std::string> lines;
  while (std::getline(std::cin, line)) {
    lines.push_back(line);
  }
  WordCounter(lines);
  return 0;
}
SashaMN
  • 708
  • 5
  • 16