#include <iostream>
#include <ctime>
#include <cstdlib>
#include <string.h>
using namespace std;
int main()
{
char pin[6]; //character array to allow for ease of input
int randomNumbers[10]; //holding the randomized numbers that are printed back to the user
int pinStorage[5];
char pinVerify[5];
char pinReenter[6];
int result;
srand(time(0));
cout << "Enter your pin number" << endl;
cin >> pin;
for (int i = 0; i < 5; i++)
{
pinStorage[i] = pin[i] - '0';
}
for (int i = 0; i < 10; i++)
{
randomNumbers[i]= rand() % 3 + 1;
}
cout << "Pin Verify: ";
for (int b = 0; b < 5; b++)
{
for (int d = 0; d <10; d++)
{
if (pinStorage[b]== d)
{
pinVerify[b] = randomNumbers[d];
switch (pinVerify[b])
{
case 1: pinVerify[b] = '1';
break;
case 2: pinVerify[b] = '2';
break;
case 3: pinVerify[b] = '3';
}
cout << pinVerify[b] << " ";
}
}
}
cout << " " << endl;
cout << "Pin : 0 1 2 3 4 5 6 7 8 9" << endl;
cout << "Number: ";
for (int c = 0; c < 10; c++)
{
cout << randomNumbers[c] << " ";
}
cout << " " << endl;
cout << "Renter pin" << endl;
cin >> pinReenter;
for(int h = 0; h < 5; ++h)
{
int digit = pinStorage[h];
pinReenter[h] = randomNumbers[digit] + '0';
}
cout << "PV: " << pinVerify;
cout << "PR: " << pinReenter;
result = (strcmp(pinVerify, pinReenter));
switch(result)
{
case 1: cout << "You did not enter the pin correctly!" << endl;
break;
case 0: cout << "Pin Entered Correctly!" << endl;
break;
case -1: cout << "You did not enter the pin correctly!" << endl;
}
The above is my code. The objective is to be able to enter a normal 5 digit pin such as 12345. The program will then store that pin, and produce a screen like this:
Pin: 0 1 2 3 4 5 6 7 8 9
Num: 3 1 2 3 2 2 3 1 1 3
The program randomized the num part that you see and assigns it to the numbers above. That way the user reenters 12322 and the computer recognizes it as him entering the right code. The next time it where to do it, it would be rerandomized to something else. This whole project is designed to prevent shoulder surfing.
However I seem to be having a problem with my code. Almost everything is working but with the final strcmp function. Even though I have pinVerify set to 5, it still gives me 5 numbers and a ASCII character at the end, something like 21323☻. This makes it impossible to ever have pinVerify and pinReenter as equal, meaning it's impossible for the program to tell you you entered in the challenge correctly, even when you did.
Can anyone help me fix this? I've been looking and tinkering for a while and have been completely unsuccessful.
C-style strings are null-terminated. In your example, it means that, when you want to work with two strings of length 5, you should actually reserve 5+1=6 chars for each of them, and make sure that the 5-th (0-indexed) char contains a character with ASCII code 0. Otherwise, strcmp, and any other C-string function, proceeds past the end of your char[5] array until it finds a byte containing zero.
Related
I'm trying to create a program that would ask the person to write 10 integers, the program should print out the integers that has not already been written, meaning it skips the duplicate integers. I know that I'm supposed to have another for loop but how am I supposed to write it?
If I would write "10, 5, 6, 5, 9, 5" it would print out "10, 5, 6, 9"
This is my current code.
int main()
{
const int target = 10;
int num[target];
cout << "Write " << target << " integers by space: ";
for (size_t i = 0; i < target; i++)
{
cin >> num[i];
cout << "[" << num[i] << "]"
<< " ";
}
};
The output is the same as the input. It never skips the same duplicate.
Some people tell me to use a nested for loop and have something like this, but I don't know how to implement it.
for (int i = 0; i < num.size(); i++) {
if (i > 0 && num[i - 1] == num[i]);
cout << num [I] << " ";
}
The easy way to do it is use both a std::unordered_set and a std::vector. The unordered_set can be used as the logic for determining whether the input is unique. If it is just add it to your vector.
A short example (with minimal input error handling) would be:
#include <iostream>
#include <unordered_set>
#include <vector>
#include <limits>
int main (void) {
std::vector<int> vi{}; /* vector of int to preserve order */
std::unordered_set<int> us{}; /* set for ensuring only unique ints */
int i = 0, n = 5;
std::cout << "enter " << n << " integers\n";
while (i < n) {
int tmp;
std::cout << " " << i+1 << ") "; /* prompt for input */
if (std::cin >> tmp) { /* validate EVERY input */
if (us.find(tmp) == us.end()) { /* if tmp not in set */
us.insert(tmp); /* insert tmp in set */
vi.push_back(tmp); /* insert tmp in vector */
}
i++; /* only increment on good input */
}
else { /* handle error */
std::cerr << " error: invalid\n"; /* display error */
std::cin.clear(); /* clear stream state */
/* clear all characters to end of line */
std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
}
}
std::cout << "\nunique integers\n";
for (const auto& v : vi)
std::cout << " " << v;
std::cout << '\n';
}
Example Use/Output
$ ./bin/vector_unique_int
enter 5 integers
1) 2
2) bananas
error: invalid
2) 4
3) 5
4) 2
5) 4
unique integers
2 4 5
Look things over and let me know if you have questions.
I managed to solve it by using bool. I still don't know how I would write it in another way, please if there is provide me with another solution.
int main()
{
const int target = 10;
int num[target];
cout << "Write " << target << " integers by space: ";
for (int i = 0; i < target; i++)
{
cin >> num[i];
bool unique = true;
for (int j = 0; j < i; j++)
if (num[j] == num[i])
{
unique = false;
break;
}
if (unique)
cout << "[" << num[i] << "]"
<< " ";
}
return 0;
}
Output Was :
Write 10 integers by space: 10 5 10 3 2 5 1 10 9
[10] [5] [3] [2] [1] [9]
Take a string from user then change the last letter to upper and write the 2nd letter and 4th letter from the string.
Generate 10 random integers from <-10,5>. Print these numbers. To the even numbers, add 100 and print them again.
I wrote this code; is it right?
#include <iostream>
#include <string>
#include<time.h>
#include <array>
using namespace std;
int main()
{
string a;
cin >> a;
cout << a << endl;
a.back() = toupper(a.back());
cout << a<<endl;
cout << "2 letter is "<<a.at(2) << endl;
cout <<" 4 letter is "<< a.at(4) << endl;
srand(unsigned(time(0)));
int tab[10];
for (int i = 0; i < 10; i++)
{
int z = (rand() % 16) - 10;
tab[i] = z;
}
for (int i = 0; i < 10; i++)
{
cout << tab[i] << endl;
}
cout << "===============" << endl;
for (int i = 0; i < 10; i++)
{
if (tab[i] % 2 == 0)
{
tab[i] += 100;
}
}
for (int i = 0; i < 10; i++)
{
cout << tab[i] << endl;
}
}
This is wrong
cout << "2 letter is "<< a.at(2) << endl;
The second letter in a string is a.at(1) because in C++ array indexes start at zero, but in English we start counting at one.
Your code is wrong! The following two lines, in particular:
cout << "2 letter is "<<a.at(2) << endl;
cout <<" 4 letter is "<< a.at(4) << endl;
Why? Because array indexes (and string positions) begin at zero in C++, so the first letter will be a.at(0) and, thus, the second letter will be a.at(1).
So, you should have this:
cout << "2 letter is " << a.at(1) << endl;
cout <<" 4 letter is " << a.at(3) << endl;
Also, for better overall coding-style guidelines, please read this: Why is "using namespace std;" considered bad practice?
for (int i = 0; i < 10; i++)
{
if (tab[i] % 2 == 0)
{
tab[i] += 100;
}
}
for (int i = 0; i < 10; i++)
{
cout << tab[i] << endl;
}
I believe this is where your problem lies. Your teacher said if they are even, print them again - and by that I think he/she means to print just the even numbers again (I am taking a liberal use of language here), so change the above to:
for (int i = 0; i < 10; i++)
{
if (tab[i] % 2 == 0)
{
tab[i] += 100;
cout << tab[i] << endl;
}
}
There are several things I would consider sub-optimal or incorrect if I was your instructor:
Accessing at(2) and at(4) will give back 3rd and 5th characters, not 2nd and 4th. Also, when you say "2 letter" and "4 letter", do you (or your instructor) mean letter #2 and letter #4, or first 2 letters and then first 4 letters. There seems to be something lost in translation here, as was already commented.
You do not check for string length before accessing characters in it. You access a.back() without checking that the string is not empty, and at(2) and at(4) without checking it is of sufficient length. This makes it very easy to crash your program, by providing insufficient characters as input (you did not provide any input assumptions, so this may be OK with your instructor).
For the second part of the program - the one with the random numbers - you are using 4 loops, when 2 would have been perfectly sufficient: you could generate the numbers, and print them in one loop. Then, you could add 100 to the even ones, and print again, in a second loop.
Finally, when writing code, be consistent with your indentation. The first part of you code is indented by 4 characters, and the second, by 8. Only indent within blocks, and keep indentation uniform for the entire block.
I am a beginner in programming. I was doing some simple applications. I was already done with my programme when I realised that my variable is getting random, even if I set it to 0. I was trying to figure it out why. My goal is to add 1 to the "cor" variable when the answer is matching the random generated number, the "else" section is working as it has to be. Maybe someone more experienced can help me.
`
#include <iostream>
#include <string>
#include <time.h>
#include <Windows.h>
using namespace std;
int number;
int ynumber[5];
int cor = 0;
int falsed = 0;
int main()
{
cout << "Welcome to our lottery!" << endl;
cout << "We start in ..." << endl;
Sleep(2000);
for (int i = 3; i >= 0; i--)
{
system("cls");
cout << i << endl;
Sleep(1000);
}
system("cls");
srand(time(NULL));
for (int i = 0; i < 6; i++)
{
cout << "Type your " << i+1 << " number below" << endl;
cin >> ynumber[i];
number = rand() % 50 + 1;
cout << "The picked number is: " << number << endl;
Sleep(1000);
if (ynumber[i] == number)
{
cout << "Same same!" << endl;
cor = cor + 1;
}
else
{
cout << "Hope for better luck next time ;)" << endl;
falsed = falsed + 1;
}
}
system("cls");
cout << "Thank you for participating!" << endl << "Correct picked numbers: " << cor << endl << "Wrong picked numbers: " << falsed << endl << endl;
system("pause");
return 0;
}
`
int ynumber[5];
The length of your array is 5
for (int i = 0; i < 6; i++)
{
//...
cin >> ynumber[i];
You loop over the indices 0,1,2,3,4,5. Use your fingers to count the number of indices that you use. You'll notice that you access the array at 6 different fingers. 6 is more than 5. As such, we can conclude that you're accessing the array out of bounds. The consequence is that behaviour of your program is undefined.
Solution: Do not access an array out of bounds. The last index of array of length n is n - 1.
More generally: Don't rely on magic numbers. In this case, you could use instead:
for (int i = 0; i < std::size(ynumber); i++)
#include <iostream>
using namespace std;
The limit is to make 10 input numbers
const int LIMIT = 10;
int main ()
{
This is just declaring variables
float counter ;
int number ;
int zeros;
int odds;
int evens;
cout << "Please enter " << LIMIT << "integers, "
<< "positive, negative, or zeros." << endl;
cout << "The numbers you entered are:" << endl;
From here I am trying to print out all the numbers that the user has inputted and checking if it is odd or even
for (counter = 1; counter <= LIMIT; counter++)
{
cin >> number;
switch(number % 2)
{
case 0:
So here I am trying to count zeros as even numbers so at the end the output of even numbers will include zero if the list has a zero
if (number == 0 ){
zeros++;
evens++;
}
case 1:
case -1:
odds++;
}
}
cout << endl;
cout << "There are " << evens << " evens,"
<<"which includes " << zeros << " zeros."
<<endl;
cout << "The number of odd numbers is: " << odds
<< endl;
}
The values should be initialized:
int zeros = 0;
int odds = 0;
int evens = 0;
Furthermore, the value of evens must be incremented for even numbers. In your code it is only incremented in the case number == 0.
switch(number % 2)
{
case 0:
if (number == 0 ) { zeros++; }
evens++;
break;
case 1:
case -1:
odds++;
}
You also need to insert a break after case 0.
I believe one of your major problems is that you don't break out of your switch case labels. For example:
int a = 7;
switch(a)
{
case 7: cout << "case 7\n";
case 1: // This will execute if case 7 doesn't have a break statement.
}
In your case:
for (counter = 1; counter <= LIMIT; counter++)
{
cin >> number;
switch(number % 2)
{
case 0: if (number == 0 )
{
zeros++;
evens++;
} // Falls straight through to the next cases. Counting evens as odds
case 1:
case -1: odds++;
}
}
And you only detect evens if number == 0, not if number modulo 2 equals 0.
Here's a rewritten version:
#include <iostream>
using namespace std;
const int LIMIT = 10;
int counter; // This is better as an int instead of a float
int number; // Also none of these variables need to be initialised
// As they are guaranteed to be zero-initialised as global static variables
int zeros;
int odds;
int evens;
int main ()
{
cout << "Please enter " << LIMIT << "integers, "
<< "positive, negative, or zeros." << endl;
for (counter = 1; counter <= LIMIT; counter++)
{
cout << "Enter number " << counter << " : ";
cin >> number;
switch (number % 2)
{
case 0:
if (number == 0) zeros++; // If input equals 0, increment zero counter
evens++; // Increment evens if in this case label
break; // Break, don't want to increment odds
default: odds++; // Default case, if not 0, must be odd.
}
}
cout << endl;
cout << "There are " << evens << " evens,"
<< "which includes " << zeros << " zeros." << endl;
cout << "The number of odd numbers is: " << odds << endl;
cin.ignore(); // This just discards the final '\n' newline character
cin.ignore(); // This blocks the program so the console doesn't close immediately
return 0;
}
I'm trying to solve one of the questions on a task sheet I've been received, to help me further in my understanding of C++ code from my class.
The question is (and I quote):
Write a program that:
Asks the user to enter 10 numbers between 1 and 5 into an array and displays the array on screen
Creates a second array of size 5 and fills it with zeros
Counts how many 1s, 2s, , … 5s have been entered into the first array and stores this number in the second array.
Displays the second array as shown in the example below.
The problem is how to go about checking how many times a number was entered. I was thinking of a for loop, but the way I wrote it is fundamentally incorrect, so I find myself struggling to see the mistake I am having. Perhaps I am missing something simple? Any help would be great.
Here is my (terrible) for loop attempt, so you can see my error.
#include <iostream>
#include <windows.h>
using namespace std;
int main()
{
int input[10];
const int MAX_NO = 5;
int COUNT[5] = { 0,0,0,0,0 };
int count = 10;
for (int i = 0; i < count; i++)
{
cout << "Please enter a number for value " << i + 1 << " :";
cin >> input[i];
while (input[i] < 1 || input[i] > 5)
{
cout << "Error: Enter another number between 1 and 5: ";
cin >> input[i];
}
}
cout << endl << "You entered ";
for (int i = 0; i < count; i++)
{
cout << input[i] << " ";
}
cout << "\n";
// show how many times 1 number appears
for (int i = 1; i <= 5; i++)
{
if (input[i] == i)
{
COUNT[i]++;
}
}
for (int i = 0; i < MAX_NO; i++)
{
cout << i + 1 << " appears " << COUNT[i]
<< " times in the input" << endl;
}
cout << endl;
system("pause");
return 0;
}
Put
COUNT[ input[i]-1 ]++;
in your first loop (after validation). Once you do that, you don't need a second loop to tally up the results.
This works from the inside out by first getting what input[i] is, then using it to modify the (input[i]-1)'th location in the COUNT array. If the user enters 4 on the first run of the loop, then i == 0 and input[i] == 4. Since arrays are 0-based, it will increment COUNT[input[i]-1] which in this case is COUNT[4-1] == COUNT[3].
After your initial loop runs the number of 1's will be in COUNT[0], the number of 2's will be in COUNT[1] and so on.
#include <iostream>
#include <windows.h>
using namespace std;
int main()
{
//declare a constant values
int input[10];
int count = 10; //all constant MUST be in capital letters
//second array filled with zeros
const int MAX_NO = 5;
int COUNT[5] = { 0, 0, 0, 0, 0 };
//ask user for 10 input values
for (int i = 0; i < count; i++)
{
cout << "Please enter a number for value " << i + 1 << " :";
cin >> input[i];
//check if input numbers are between 1 and 5 inclusive
while (input[i] < 1 || input[i] > 5)
{
cout << "Error: Enter another number between 1 and 5: ";
cin >> input[i];
}
/* show how many times 1 number appears.
this section should be in the main loop which would enable the program to check how many times a
number is entered so that it is stored in the second array. changed i to secondCount because this is the counting index of the second array not the first which you've called i (one of the reason you'd all zero as output when u ran your code)*/
for (int secondCount = 1; secondCount <= MAX_NO; secondCount++)
{
if (input[i] == secondCount)
{
COUNT[secondCount-1]+= 1; //use minus 1 from i and increment. += 1 is the same as COUNT++
}
}
}
//display number entered in the first array
cout << endl << "You entered ";
for (int i = 0; i < count; i++)
{
cout << input[i] << " ";
}
cout << "\n";
//display how many times a number is entered.
for (int secondCount = 0; secondCount < MAX_NO; secondCount++)
{
cout << secondCount + 1 << " appears " << COUNT[secondCount]
<< " times in the input" << endl;
}
cout << endl;
system("pause");
return 0;
}
OUTPUT:
Please enter a number for value 1 = 1
Please enter a number for value 2 = 1
Please enter a number for value 3 = 1
Please enter a number for value 4 = 2
Please enter a number for value 5 = 3
Please enter a number for value 6 = 2
Please enter a number for value 7 = 4
Please enter a number for value 8 = 4
Please enter a number for value 9 = 3
Please enter a number for value 10 = 2
You entered: 1 1 1 2 3 2 4 4 3 2
1 appears 3 times in the input
2 appears 3 times in the input
3 appears 2 times in the input
4 appears 2 times in the input
5 appears 0 times in the input
for (int i = 1; i <= 5; i++)
{
if (input[i] == i)
{
COUNT[i]++;
}
}
Let's examine what this is doing. It starts by checking input[1]. (This should be input[0] as array indices start at 0). Then it checks if input[1] is equal to 1. If it is, then it increments COUNT[1].
Next, it checks input[2]. Then it checks if input[2] is equal to 2. If it is, it increments COUNT[2]. And so on until it has gone through input[5].
Do you see the problem with this? You're only checking the first 5 inputs and only checking them against a single value.