1. ## Another simple program

Hi everyone,

I've been working through the loops section of jumping into c++ and made a small 'maths quiz'. I wanted a random number i.e. rand() for numA and numB (1,2,3,4,5,6,7,8,9 or 10) but haven't managed that yet so I set them manually instead for now.

#include <cstdlib> is in there because I read that is needed for rand() to work. Once again, not sure why, includes will come later I expect.

Here's the quiz:

Code:
```#include <iostream>
#include <cstdlib>

using namespace std;

int main ()
{
int numA = 5;
int numB = 5;
int answer = numA + numB;
int guess;

for ( int attempts = 1; !(guess==answer); attempts++ )
{

cout << "What is " << numA << " + " << numB << "? ";
cin >> guess;
cin.ignore();

{
cout << "Well done, got it in: " << attempts << " attempts!\n";
break;
}
else
{
if ( attempts < 3 )
{
cout << "Incorrect. Please try again.\n";
}
else
{
cout << "Sorry, run out of attempts! Game over...";
break;
}
}
}
}```
What I wanted to know is whether or not this would be the correct use of the 'break' command. I thought maybe the loop would handle when a game is over or not i.e. after 3 wrong guesses, or a correct answer, cease looping. Adding break in like this seems wrong to me, but of course, not sure why.

Any feedback is more than welcome. Maybe a pointer for a better way of achieving this or what I've done wrong. I'd rather suggestions than solutions, I wont learn anything copying and pasting!

Sam.

2. Your use of break seems okay.
For random numbers, mod (%) the output of rand() with n+1 to get a random no. within 1 (or 0, I'm not sure) and n;
Some points:
1.Why, though, is the cin.ignore() there ?
2.guess needs an initial value, which should not be equal to the correct answer.
4.You could write this using boolean flags...which would make the loop simpler. Whether it is desirable depends on the opinion of the programmer.

3. Originally Posted by manasij7479
Your use of break seems okay.
For random numbers, mod (%) the output of rand() with n+1 to get a random no. within 1 (or 0, I'm not sure) and n;
Some points:
1.Why, though, is the cin.ignore() there ?
2.guess needs an initial value, which should not be equal to the correct answer.
4.You could write this using boolean flags...which would make the loop simpler. Whether it is desirable depends on the opinion of the programmer.
Thanks for the feedback.

1) cin.ignore() is probably not needed. I put it there because I was working on another similar program that needed it! Bad habits already?
2) Is guess not populated by the users input? I didn't think it required an initialisation value. Will look into this.
3) Ok

Sam.

4. Originally Posted by samwillc
Thanks for the feedback.

1) cin.ignore() is probably not needed. I put it there because I was working on another similar program that needed it! Bad habits already?
2) Is guess not populated by the users input? I didn't think it required an initialisation value. Will look into this.
3) Ok

Sam.
1) There is a similar use of cin.ignore() for error handling.. but you can probably forget about that for a while.
2) Yes, but guess is checked before the user gives the first input. The condition of the for loop checks guess. So, if guess accidentally has the same value as the answer, the loop won't run.

5. One more comment is your formatting. It's inconsistent.

The contents of the FOR loop should be indented...

6. Originally Posted by manasij7479
1) There is a similar use of cin.ignore() for error handling.. but you can probably forget about that for a while.
2) Yes, but guess is checked before the user gives the first input. The condition of the for loop checks guess. So, if guess accidentally has the same value as the answer, the loop won't run.
I understand, thanks. I do however think it's important to start learning error handling as early on as possible. My other program took a password, and had to make sure if a user was to enter 'password <space> anotherword' that only the first word is taken and anything subsequent is ignored.

Originally Posted by WaltP
The contents of the FOR loop should be indented...
Ok great, thanks for the feedback.

Sam.

7. The structure of your loop is abit strange, i won't post an entire program because that won't teach you anything, but consider using the following for loop:

Code:
`for ( int attempts = 1; attempts <= 3; attempts++ )`

8. @Neo1, I will adapt my program. I was going to use <=3 but I figured <4 would do the same thing. I will try both and see if it does.

I was trying to base this on something I had programmed in sense (a derivative of scratch). It has come in quite useful so far for teaching the basics. This is a similar maths quiz I built using sense, as you can see it's much simpler with the UI, you don't have to be concerned with curly brackets/indentation or any of that. Obviously I want to learn some 'proper' programming now!

http://dl.dropbox.com/u/63070476/Scr...%3A36%3A55.png

Sam.

9. Originally Posted by samwillc
I do however think it's important to start learning error handling as early on as possible.
It is a little tricky to get right.
Here is a loop that repeatedly asks the user to enter a number, unless he chooses to quit by pressing y.
Code:
```while(true)
{

int n;
cout<<"Enter a number: ";
cin>>n;
cout<<"You entered "<<n<<".\n";

char q;
cout<<"Quit ?(y/n)\n";
cin>>q;
if(q=='y'||q=='Y')
break;
else
cin.ignore(numeric_limits<streamsize>::max(), '\n');
}```
Now comment out the ignore statement and enter a word (Say, "yes" instead of "y") and the program will crash. The ignore prevents that.
(You'll need to include the <limits> header for this.)

10. Originally Posted by samwillc
This is a similar maths quiz I built using sense, as you can see it's much simpler with the UI, you don't have to be concerned with curly brackets/indentation or any of that.

11. Originally Posted by manasij7479
It is a little tricky to get right.
Here is a loop that repeatedly asks the user to enter a number, unless he chooses to quit by pressing y.
Code:
```while(true)
{

int n;
cout<<"Enter a number: ";
cin>>n;
cout<<"You entered "<<n<<".\n";

char q;
cout<<"Quit ?(y/n)\n";
cin>>q;
if(q=='y'||q=='Y')
break;
else
cin.ignore(numeric_limits<streamsize>::max(), '\n');
}```
Now comment out the ignore statement and enter a word (Say, "yes" instead of "y") and the program will crash. The ignore prevents that.
(You'll need to include the <limits> header for this.)
Sorry, it wont compile using geany:

1) loop-quit-on-y.cpp:22:20: error: ‘numeric_limits’ was not declared in this scope
2) loop-quit-on-y.cpp:22:45: error: expected primary-expression before ‘>’ token
3) loop-quit-on-y.cpp:22:52: error: no matching function for call to ‘max()’

Not sure how to test this.

I added include iostream, int main etc... around this btw, didn't just copy and paste the above and try and run it!

Sam.

12. Originally Posted by samwillc
@Neo1, I will adapt my program. I was going to use <=3 but I figured <4 would do the same thing. I will try both and see if it does.

I was trying to base this on something I had programmed in sense (a derivative of scratch). It has come in quite useful so far for teaching the basics. This is a similar maths quiz I built using sense, as you can see it's much simpler with the UI, you don't have to be concerned with curly brackets/indentation or any of that. Obviously I want to learn some 'proper' programming now!

http://dl.dropbox.com/u/63070476/Scr...%3A36%3A55.png

Sam.
Whether you use <= 3 or < 4 doesn't matter at all, i find <= 3 marginally more readable for this particular purpose, but since for loops are used for iterating arrys, you will see < used very frequently.

In regards to your old program: Many programmers have tried to convert a program from one language to another, many have died horrible deaths doing it. Okay maybe not, but it usually doesn't work out. Don't translate from one program to another directly, forget your old solution, think about the problem from scratch (no pun, i swear) and come up with a solution based on the tools you have in C++ so far.

13. Originally Posted by samwillc
Sorry, it wont compile using geany:
#include<limits>

14. Originally Posted by Neo1
Whether you use <= 3 or < 4 doesn't matter at all, i find <= 3 marginally more readable for this particular purpose, but since for loops are used for iterating arrys, you will see < used very frequently.

In regards to your old program: Many programmers have tried to convert a program from one language to another, many have died horrible deaths doing it. Okay maybe not, but it usually doesn't work out. Don't translate from one program to another directly, forget your old solution, think about the problem from scratch (no pun, i swear) and come up with a solution based on the tools you have in C++ so far.
Lol, I think you're right. I can already see the problems in trying to directly translate this. They seem to handle things in different ways which I have found trying to convert some other programs! No horrible death though, just a few hours of frustration. Nothing to put me off though!

Sam.

15. You should also be made aware that taking the result of rand() modulus some number is not the only way to use rand(). For small ranges especially it can be undesirable because of the way it will make rand() actually favor one outcome more than others. Say you wanted to get a number from 0 to 4 inclusive from rand().
Code:
`int r = rand()%5;`
It turns out that you can get 0 two different ways: rand() could return 5 and the result modulus 5 would be 0, or rand() could just return 0 because 0 modulus anything positive is definitely 0 again. That's the way a lot of programmers learn to do it very early because it's easy to teach.