-4

It's a college project, all it has to do is ask the user for info and then output it. That part is done, so the project is done (I'm not asking for help with school work).

I decided to add a bit more to it just for fun. I'm trying to make it know when nothing was entered by the user (just hitting enter) and tell the user to do so and start over. After it starts over more than once, it outputs the last "cout" however many times the user failed to answer something (by just hitting enter). I can't figure out why.

Output:

Answer every question in order for this word game to work properly.

What is your name? 12

How old are you? 12

Where are you from? 12

What's the name of your college? 12

What is your profession? 12

What type of animal is your pet? 12

and what is her/his name? 12

There once was a person named 12 who lived in 12. At the age of 12, 12 went to college at 12. 12 graduated and went to work as a 12. Then, 12 adopted a(n) 12 named 12. They both lived happily ever after!

There once was a person named 12 who lived in . At the age of 12, 12 went to college at 12. 12 graduated and went to work as a . Then, 12 adopted a(n) 12 named 12. They both lived happily ever after!

There once was a person named 12 who lived in 12. At the age of 12, 12 went to college at 12. 12 graduated and went to work as a 12. Then, 12 adopted a(n) named 12. They both lived happily ever after!

Press any key to continue . . .

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

int main()
{
    string name, city, college, prof, animal, petn;
    int age;

    // If no value is given for a question, start over.
    struct NoValue
    {
        static void check(string a, int cls = 100)
        {
            if (a.empty())
                {
                cout << "\n\nAnswers cannot be blank, let's try this again..." << endl;
                cin.get();      // Pause
                for (int i = 0; i <= cls; i++)  //
                    cout << "\n" << endl;               // Clear screen
                main();
            }
        }
    };

    cout << "Answer every question in order for this word game to work properly.\n\n";

    // Questions
    cout << "What is your name? ";
    getline(cin, name);

    cout << "How old are you? ";
    cin >> age;
    cin.ignore(); // To prevent the program from printing out the next 2 questions in the same line.

    cout << "Where are you from? ";
    getline(cin, city);

    cout << "What's the name of your college? ";
    getline(cin, college);

    cout << "What is your profession? ";
    getline(cin, prof);

    cout << "What type of animal is your pet? ";
    getline(cin, animal);

    cout << "and what is her/his name? ";
    getline(cin, petn);

    NoValue::check(name);
    NoValue::check(city);
    NoValue::check(college);
    NoValue::check(prof);
    NoValue::check(animal);
    NoValue::check(petn);

    cout << "\nThere once was a person named " << name << " who lived in " << city 
    << ".  At the age of " << age << ", " << name << " went to college at " << college 
    << ".  " << name << " graduated and went to work as a " << prof << ".  Then, " << name 
    << " adopted a(n) " << animal << " named " << petn << ".  They both lived happily ever after!\n\n" << endl;

    return 0;
}
  • 10
    Supplement your formal education with these [C++ books](https://stackoverflow.com/questions/388242/the-definitive-c-book-guide-and-list). You will need it if you are to pursue a career that of a C++ developer. – Ron Jan 23 '18 at 20:29
  • 7
    C++ forbids calling `main`. If that works it's by accident. – Cheers and hth. - Alf Jan 23 '18 at 20:33
  • 1
    I did not understand what do you want know – Andam Jan 23 '18 at 20:34
  • Anyway, is it reasonable to require the user to enter everything so far, again, when he or she just presses return? I'd abstract the input of the value as a function that asks repeatedly. – Cheers and hth. - Alf Jan 23 '18 at 20:34
  • 1
    *"Confused over something that most likely has a simple answer"* is a terrible question title. – Christian Hackl Jan 23 '18 at 20:53
  • Again, this is just something I was trying to do (just because). I'm aware that it's not the best way to achieve it and that it's probably not even necessary. I'm just asking if anyone knows why this happens. – Daniel Diaz Jan 23 '18 at 21:10

3 Answers3

1

You wrote:
"I can't figure out why.";
So I'll assume that the question is:
"Can you guys help me figure out what is happening so that I can find a fix?"

If that is the case, here is what is going on.

the main starts for the first time (let's name this FIRST_MAIN).

In the FIRST_MAIN the "user" missed the animal type when executing the row

cout << "What type of animal is your pet? ";
    getline(cin, animal);

but the FIRST_MAIN continued executing and started checking the user inputs.
When the FIRST_MAIN start executing the row

NoValue::check(animal);

Inside the check method (for the animal type) the FIRST_MAIN prints the error message, clears the screen and STARTS A SECOND_MAIN.

NOTE: Now that the SECOND_MAIN id running the FIRST_MAIN is waiting for the SECOND_MAIN to complete. REMEMBER that the FIRST_MAIN has to complete the check method and continue executing the remaining rows

Let's suppose that now (in the SECOND_MAIN) the user do averything right, and all the checks are ok.
Now the SECOND_MAIN prints out the story and the the SECOND_MAIN reaches for the row

return 0

who called SECOND_MAIN?
it was FIRST_MAIN that called SECOND_MAIN!
So SECOND_MAIN wakes up the FIRST_MAIN that was waiting for the SECOND_MAIN to complete.

So, the FIRST_MAIN will continue executing rows from

main();

inside the check function (where FIRST_MAIN called SECOND_MAIN).

Now, FIRST_MAIN completes the check (for the animal type missed) and continues with che next row

NoValue::check(petn);

And HERE the FIRST_MAIN prints out AGAIN the story with the MISSING animal type.

I think that now you figured out what is happening.
How to fix this? this is another question :-)

alp
  • 389
  • 2
  • 5
0

You have the method check, that checks for blank input and if it is blank, calls main. The problem is that once that has finished, it resumes from where check was called. I would recomend having check return a bool, indicating whether to continue checking and printing, along the lines of:

if(!NoValue::check(name))
    return 0;
BillThePlatypus
  • 362
  • 1
  • 14
0

Simply check with strtol if the entered string is a number. If it is a number store the value only if a when numeric value are asked otherwise return a error. If a string value is asked but the user inser a numeric value give a error.

Here a reference for strtol

P.Carlino
  • 661
  • 5
  • 21