Making the user give a boolean input with while loop - c++

I have just started learning C++ and trying to learn the syntax.
#include <iostream>
#include <limits>
using namespace std;
int main(){
bool answer;
cout << "Did you enjoy testing this program? (1 for yes, 0 for no) ";
cin >> answer;
while (!(cin >> answer)) {
cout << "Invalid value!\n";
cin.clear();
cin.ignore(numeric_limits<streamsize>::max(), '\n');
cout << "Please type either 0 or 1: ";
cin >> answer;
}
cout << "Your feedback has been registered. Feedback: " << answer;
}
The aim is to keep making the user ask over and over until they input either 0 or 1. The code snippet just makes things freeze when either of those values is given. How should this be fixed?

The cin >> answer; statement above the loop, and the cin >> answer; statement at the end of the loop body, both need to be removed.
You are prompting the user to enter a value, then you read in that value and ignore it, and then you wait for the user to enter in another value, even though you didn't prompt the user to enter more than 1 value.
If they do happen to enter a 2nd value, and it fails, your loop will then prompt the user to enter in a new value, then you read in that value and ignore it, and then you wait for the user to enter yet another value without prompting the user to do so.
You should be invoking cin >> answer only 1 time per loop iteration, eg:
#include <iostream>
#include <limits>
using namespace std;
int main(){
bool answer;
cout << "Did you enjoy testing this program? (1 for yes, 0 for no) ";
// cin >> answer; // <- remove this!
while (!(cin >> answer)) {
cin.clear();
cin.ignore(numeric_limits<streamsize>::max(), '\n');
cout << "Invalid value!\n";
cout << "Please type either 0 or 1: ";
// cin >> answer; // <- remove this!
}
cout << "Your feedback has been registered. Feedback: " << answer;
}

Related

Getting error saying no match for 'operator=='. Trying to get if statement to realize if user answered 'n' then print message

Code is diagnostic program, asks y or n questions then using if statements will give diagnosis. Asks four yes or no questions and if first two answers are n then diagnosis is unknown but if first to are yes and third is yes user has a cold. I haven't typed out full code yet but all questions are shown and first if statement there back an error.
#include <iostream>
#include <string>
#include <cmath>
using namespace std;
int main()
{
// variables
string runnyNose;
string congestedNose;
string achyBody;
string severeHeadache;
double bodyTemp;
// Print program name
cout << "==================================" << endl;
cout << "Welcome to Dr. Plympton's Office!" << endl;
cout << "==================================" << endl;
// get runny nose symptom
cout << "Do you have a runny nose (Enter 'y' or 'n')? ";
cin >> runnyNose;
// get congestion symptom
cout << "Are you expeeriencing nasal congestion (Enter 'y' or 'n')? ";
cin >> congestedNose;
// get achy symptom
cout << "Are you feeling achy all over (Enter 'y' or 'n')? ";
cin >> achyBody;
// get headache symptom
cout << "Do you have a severe headache behind or below one eye (Enter 'y' or 'n')? ";
cin >> severeHeadache;
// get temp
cout << "What is your temperature (Enter the number)? ";
cin >> bodyTemp;
if (runnyNose == 'n')
cout << "Unknown: Sorry, you need to see a specialist. Your bill is $40.00. " <<
endl;
return 0;
}
try to change the data-type from string to char. You can compare them with strcmp or only with ==.

While loop not waiting for user input (while datatype is invalid)

Trying to check if cin obtained valid input (eg - no string or char in int variable), but the while loop gets stuck at an infinite loop and doesn't even wait for user input
#include <iostream>
#include <string>
using namespace std;
int main(){
cout << "How many would you like to buy ? ";
int buyAmt;
cin >> buyAmt;
while (!cin) {
cin.clear();
cin >> buyAmt;
cout << "Sorry, you must enter an integer" << endl << endl;
}
}
Expected result:
How many would you like to buy ? fdssd
Sorry, you must enter an integer (asks for usr input here)
Actual result:
How many would you like to buy ? fdssd
Sorry, you must enter an integer
Sorry, you must enter an integer
Sorry, you must enter an integer
Sorry, you must enter an integer
Sorry, you must enter an integer
Sorry, you must enter an integer
After applying cin.clear(); you need to consume the wrong input first, before applying cin >> buyAmt; again.
Something like
while (!cin) {
std::string dummy;
cin.clear();
cin >> dummy;
cout << "Sorry, you must enter an integer" << endl << endl;
cout << "How many would you like to buy ? ";
cin >> buyAmt;
}

Why cin inside while doesn't stop to get user input?

I'm starting now with C++, so I imagine this is gonna be a very easy-newbie question.
Well, why the "cin >> x" line inside while doesn't stop the loop to get the user input (if the user inputs a character, in place of a number)?
#include <iostream>
using std::cin;
using std::cout;
using std::endl;
int main()
{
int x = 0;
cout << "Please, enter x: ";
cin >> x;
while (!cin)
{
cout << "Please, it must be a number!\n";
cin >> x;
}
cout << "Thanks!.";
cin.ignore();
cin.ignore();
}
I'm barely two days studiying C++, so I'm completely blind about what "cin" really is. I tried with "cin.sync()" and "cin.clear()", but still no luck.
And I know it is impossible to do something like "cin=true", or "cout << cin".
Well, your program should be corrected slightly
#include <iostream>
using std::cin;
using std::cout;
using std::endl;
int main()
{
int x = 0;
cout << "Please, enter x: ";
cin >> x;
while (!cin)
{
cin.clear();
cin.ignore(10000, '\n');
cout << "Please, it must be a number!" << endl;
cin >> x;
}
cout << "Thanks!.";
}
This way it works as expected. More info about it here. In general, you need to clear all the errorneous stuff from cin.
if user input a character than it will take the ascii value of character so it will not stop.
To stop the loop enter 0.

Using a while loop to check for input errors within a switch case

I have a switch in which one case asks the user for several inputs to use for constructing a class object. One of these inputs should be in the form of a number. If a number is not entered it breaks the switch and ends up terminating the program. I want to set up a while(){} condition so that if a non integer is entered it will prompt the user to enter an integer and then continue on with the program.
int main(){
int in_yob, ranking;
string in_first_name, in_last_name, in_genre, in_fact, last_name, in_composer;
char selection, choice;
do {
DisplayMenu();
cin >> selection;
cout << endl;
while (!cin || selection < 48 || selection > 53){
cin.clear();
cout << "Please make a valid selection" << endl;
DisplayMenu();
cin >> selection;
}
switch (selection) {
case 49 : {
cout << "First Name: ";
cin >> in_first_name;
cout << "Last Name: ";
cin >> in_last_name;
cout << "Genre: ";
cin >> in_genre;
cout << "Year of Birth: ";
cin >> in_yob;
cout << "Fact: ";
cin >> in_fact;
last_name = in_last_name;
transform(last_name.begin(), last_name.end(), last_name.begin(), ::tolower);
Composer& last_name = myDB.AddComposer(in_first_name, in_last_name,
in_genre, in_yob, in_fact);
cin.clear();
} break;
...
default:
cout << "Please make a valid selection" << endl;
}
} while (selection != 48);
}
I have tried inserting a while loop after cin >> in_yob; as:
while(!cin || in_yob > 1){
cin.clear();
cout << "Enter a positive enter for year of birth: ";
cin >> in_yob;
}
but the result is an infinite loop of "Enter a positive enter for year of birth: ". I know this construct for error checking works outside of a switch case so what is the reason that within a switch case i'm getting this result? Also how would you go about fixing this so that I can check for and prevent an input error? Thanks.
[To explain my self with more space and better formatting better than in a comment I post this as an answer instead as of a comment.]
When you enter input, like for example
1
the input buffer actually contains two characters, firs the digit '1' and then the newline '\n'.
When you read a single character, the input operation extracts the first character, the digit, and writes it to your variable.
If you then read another character, it will read the newline, and not whatever comes after.
There is a trick to "ignore" characters until, for example, a newline, and that is done by using the std::istream::ignore, and if you follow the link to the reference you will see a very good example on how to ignore anything up to and including the newline.
So in your case it's not enough to just call clear you need to call ignore as well in your input validation loop. And if you continue to read single characters, you need to call ignore before that as well.
You needed to clear the input stream.
#include <iostream>
#include <string>
int in_yob = 0;
int main()
{
while(std::cin.good() && in_yob < 1){
std::cin.clear();
std::cout << "Enter a positive enter for year of birth: ";
if( !(std::cin >> in_yob) ) {
std::cin.clear();
std::cin.ignore(10000,'\n');
}
}
std::cout << "YOB " << in_yob << std::endl;
}

C++ quick issue on getline(cin, string)

Its been a while since i have coded c++ and i have forgot an annoying thing that happens when you gather string input. Basically if this loops back through, say if you use negative numbers then it skips the cin from the employee name line the second go round. I remember having this issue before and having to clear or do something of that sort before or after the string is input. Please help!
PS Also for extra help can anyone help me with a correct loop below. How can i check for a value in the string input to make sure they input a value?
#include <string>
#include <iostream>
#include "employee.h"
using namespace std;
int main(){
string name;
int number;
int hiredate;
do{
cout << "Please enter employee name: ";
getline(cin, name);
cout << "Please enter employee number: ";
cin >> number;
cout << "Please enter hire date: ";
cin >> hiredate;
}while( number <= 0 && hiredate <= 0 && name != "");
cout << name << "\n";
cout << number << "\n";
cout << hiredate << "\n";
system("pause");
return 0;
}
You want to change your loop condition to be whether or not any of the below are not set. The logical AND will only trigger if all three are unset.
do {
...
} while( number <= 0 || hiredate <= 0 || name == "");
Next, use cin.ignore() as prescribed by #vidit to get rid of issues with reading in newline characters.
Lastly, and importantly, your program will run an infinite loop if one enters an alphabetic character for an integer instead of...an integer. To mitigate that, use isdigit(ch) from the <cctype> library.
cout << "Please enter employee number: ";
cin >> number;
if(!isdigit(number)) {
break; // Or handle this issue another way. This gets out of the loop entirely.
}
cin.ignore();
cin leaves a newline character(\n) in the stream, which causes the next cin to consume it. There are many ways of getting around that. This is one way.. using ignore()
cout << "Please enter employee name: ";
getline(cin, name);
cout << "Please enter employee number: ";
cin >> number;
cin.ignore(); //Ignores a newline character
cout << "Please enter hire date: ";
cin >> hiredate;
cin.ignore() //Ignores a newline character