Mike Irish
Mike Irish

Reputation: 960

C++ getline is not empty when no input is entered

I am new to c++ and still trying to wrap my head around how input/output streams work.

I am currently trying to write a function to make sure the user enters an int, and tell them if the input is empty or not a valid int.

I am using getline and have tried using cin.clear and cin.ignore but i cannot seem to get this to work and have no idea where i am going wrong.

It works if I input a letter however if i just press enter with nothing input it doesn't say no input detected.

void testStuff()
{
    string number;

    ws(cin);//skips Whitespaces

    if (getline(cin, number) && number.end() !=
        find_if_not(number.begin(), number.end(), &isdigit))
    {
        if (number.empty())
        {
            cout << "No input detected" << endl;
            testStuff();
        }
        cout << "Please input a Valid number" << endl;
        testStuff();
    }
}

Upvotes: 0

Views: 2878

Answers (2)

Jerry Coffin
Jerry Coffin

Reputation: 490768

Assuming your ws works as specified (skips whitespace in the input), by the time you call getline, something other than whitespace has to have been entered. Thus, when getline gets called, that non-whitespace character has to be waiting in the input buffer, and getline must return a non-empty sequence of characters (i.e., everything from that first non-whitespace character up to the next new-line).

For example, let's write our own ws that shows what character(s) it's skipping over:

void ws(std::istream &is) {
    while (std::isspace(is.peek())) {
        char ch;
        is.get(ch);
        std::cout << "Read: " << (int)ch << '\n';
    }
}

Now, when we call testStuff() and just press enter, we get Read: 10 as our output--i.e., ws has read and skipped the new-line we entered.

So, to get to the call to getline, the user has to enter something other than whitespace, and a new-line is whitespace. So, but the time getline is called at all, we know there's some non-whitespace character waiting in the input buffer, so when getline is called, it must produce a non-empty result.

Upvotes: 3

user6889435
user6889435

Reputation:

I have assumed that every of function(s) that i don't know implementation are written correctly. Then, I have such code (simplified):

#include <iostream>
#include <string>
using namespace std;

int main() {
    string number;
    if (getline(cin, number))
    {
        if (number.empty())
        {
            cout << "No input detected" << endl;
            main();
        }
        cout << "Please input a Valid number" << endl;
        main();
    }
}

I don't know find_if_not(number.begin(), number.end(), &isdigit) implementation so I skipped it. I've put source code on Ideone.com, you can view it HERE. After passing "just enter", program behaves vaildly. This means, one of function implementations that you didn't show us is working incorrectly. To help you we need full source code (if not, just only needed parts). Also, you should skip "using namespace std;". I think, number.end() != find_if_not(number.begin(), number.end(), &isdigit)) is implemented incorrectly. You should think about what someone told you in comments - "If the string is empty the only thing find_if_not can return is number.end(). number.end() == number.end() and body is not entered."

Upvotes: 1

Related Questions