If-construct advice needed - c++

I have a for loop in which I placed several if statements. The objective of these conditionals is to check divisibility of a number and then output a string if the number is divisible by 3. If the number is divisible by 5, another string will be outputted. However, if the number is divisible by both 3 and 5, an entirely different string will be outputted in its place instead of the other strings.
Here is my code:
for (i = 1; i <= file_int; i++){
if (i % 3 == 0) {
printf("Hoppity \n");
}
if (i % 5 == 0) {
printf("Hophop \n");
}
if (i % 5 == 0 && i % 3 == 0) {
printf("Hop \n");
}
}
As you can see, the last conditional doesn't quite work. What type of control construct should I use? else?
Thanks alot.

for (i = 1; i <= file_int; i++){
if (i % 5 == 0 && i % 3 == 0) {
printf("Five and three\n");
} else if (i % 3 == 0) {
printf("Three\n");
} else if (i % 5 == 0) {
printf("Five\n");
} else {
printf("None of the conditions passed\n");
}
}

I would use else-ifs and make us of the fact that
(i % 5 == 0 && i % 3 == 0) <=> (i % 15 == 0):
for (i = 1; i <= file_int; i++){
if (i % 15 == 0)
printf("Hop \n");
else if (i % 3 == 0)
printf("Hoppity \n");
else if (i % 5 == 0)
printf("Hophop \n");
}
Of course you can also get away without using any control structures except the for-loop at all:
const char* values[15] = {"Hop \n", "", "", "Hoppity \n", "",
"Hophop \n", "Hoppity \n", "", "", "Hoppity \n",
"Hophop \n", "", "Hoppity \n", "", ""};
for (int i = 1; i <= 100; i++)
printf(values[i % 15]);
That solution is slightly insane for this example, but it shows how you can do things differently (and it's not so farfetched when writing code where you shall never ever have more then a certain number of branch paths in one function (overzealous coding conventions...)).

Just for the sake of it, and not recommending it, as it can be harder to read as it abuses conversions from bool to int:
int msg = (i % 3 == 0) + 2*(i % 5 == 0);
switch ( msg ) {
case 3:
cout << "Multiple of 3 and 5";
case 2:
cout << "Multiple of 5";
case 1:
cout << "Multiple of 3";
}
which can be further condensed into:
const char* msgs[] = { "", "Multiple 3", "Multiple 5", "Multiple 3 and 5" };
cout << msgs[ (i%3==0) + 2*(i%5==0) ];
Of course, both solutions are against the question itself, as they are not if constructs, but rather avoid the use of if in the first case, and branches in general in the second case.

An alternative solution, keeping closer to your original code. Although the else solution is indeed more efficient (and elegant).
for (i = 1; i <= file_int; i++){
if (i % 3 == 0 && i % 5 != 0) {
printf("Hoppity \n");
}
if (i % 5 == 0 && i % 3 != 0) {
printf("Hophop \n");
}
if (i % 5 == 0 && i % 3 == 0) {
printf("Hop \n");
}
}

Related

Comparison inside while loop c++

I am trying to make when user types number, program should repeat that many times chosing random if
Here is my code
cin >> d;
c = 0;
while (c < d) {
c = c++;
num = (rand() % 3) + 1;
if (num == 1) {
system("start C:\\viewver\\vw");
Sleep(2000);
}
else if (num == 2) {
system("start C:\\viewver\\vw2");
Sleep(2300);
}
else if (num == 3) {
system("start C:\\viewver\\vw3");
Sleep(1800);
}
It always chooses to open first one and then stops.
Use == not =
if (num == 1) {
system("start C:\\test\\vw");
Sleep(2000);
}
else if (num == 2) {
system("start C:\\test\\vw2");
Sleep(2300);
}
else if (num == 3) {
system("start C:\\test\\vw3");
Sleep(1800);
}
== is for comparison, = is for assignment
The reason why it always chooses the first option is because C++ (and C) has the notion of truthy values. So any value that is not 0 is considered truthy, whereas values that evaluate to 0 are considered falsy.
In your original code, when you assign num to 1, the value of num is truthy, therefore that branch is always taken

C programming , array not printing properly

So for class we are doing some encryption/ decryption algorithms with prime numbers. I am in the first part of making the program. I am trying to get the program to check if a number is prime or not. After this, I want the program to store all prime numbers before that number in an array called prime_array. And I was trying to get those results to print out on the screen. It's not working the way I intended. I'm later going to use this in decryption of something a bit more complex. Just wandering if anyone could see what part of my code is causing the issues.
Code:
#include <stdio.h>
int main()
{
int n;
int prime;
int prime_array[1000];
int prime_answer;
int j=0;
printf("enter a number for n : ");
scanf_s("%d", &n);
if (n % 2 == 1)
{
printf("Number is prime.");
getchar();
getchar();
for (int i = 0; i <= n; i++)
{
if (n - 1 % 2 == 1)
{
n--;
prime_array[j] = n;
j++;
}
else
{
// do nothing
}
}
}
else if (n % 2 == 0)
{
printf("Number is not prime.");
getchar();
getchar();
}
for (int k = 0; k<= 10; k++)
{
printf("\n\n %d",prime_array[k]);
if (k == 10);
{
getchar();
getchar();
}
}
}
Problem is this condition-
if (n - 1 % 2 == 1)
This exression is treated as (n-(1 % 2))==1 , because % has higher precedence than - ,therefore , 1 % 2 is evaluated first .As 1 % 2 is 1 and expression become n-1 ,so condition will not be true until n is 2 (not as you would desire ) .
You need to write like this -
if ((n - 1) % 2 == 1)

NIM game against PC beginner

My professor gave me a asignment to write a 16 matches Nim game.
One part of a task is to make PC to make moves as well. So, I tried to solve the problem by using SRAND but PC picked the same row and the same amount of sticks. What is more, PC also takes emty rows wich and hits the wall when he takes the zero massive.
So, thats is what I hve already done. Any thoughts?
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#define row 4
int main()
{
int theChecker = 1, sticks[row] = {1,3,5,7}, stickSum, i, choiceRow, choiceStick, pcRow, pcStick;
char answer;
do
{
printf("\n\n\t ************ \n");
printf("\t *THE NIM GAME* \n");
printf("\t ************ \n\n");
stickSum = sticks[0] + sticks[1] + sticks[2] + sticks[3];
while(stickSum > 0)
{
printf("\nStick log:\n");
for(i = 0; i < row; i++)
printf("Row %d: %d\n", i+1, sticks[i]);
printf("\n");
if(theChecker == 1)
{
printf("Choose a row: ");
scanf("%d", &choiceRow);
printf("Choose a sick: ");
scanf("%d", &choiceStick);
while((choiceRow <= 0) || (choiceRow > 4) || (sticks[choiceRow - 1] < choiceStick) || (choiceStick == 0))
{
printf("\n\t !!!ERROR!!!\n\tInvalid row or stick\n\nCheck stick log above\n\n");
printf("Choose a row: ");
scanf("%d", &choiceRow);
printf("Choose a sick: ");
scanf("%d", &choiceStick);
}
sticks[choiceRow-1] -= choiceStick;
stickSum -= choiceStick;
}
else //pc move starts-------------------------------------------
{
while(((pcRow <= 0) || (pcRow > 4)) && sticks[choiceRow - 1] == 0)
{
time_t seconds;
seconds = 0;
time(&seconds);
srand((unsigned int)seconds);
pcRow = rand() % 4;
}
printf("PC ROW: %d\n", pcRow);
while((sticks[pcRow - 1] < pcStick) || (pcStick == 0))
{
time_t seconds2;
seconds2 = 0;
time(&seconds2);
srand((unsigned int)seconds2);
pcStick = rand() % 16;
}
printf("PC STICK: %d\n\n", pcStick);
sticks[pcRow-1] -= pcStick;
stickSum -= pcStick;
}
if((theChecker == 1) && (stickSum == 0))
printf("\n\n!!!GAME OVER!!! You took the last stick!!!\n\n");
else if((theChecker == 2) && (stickSum == 0))
printf("\n\n!!!CONGRATS!!! You won!!!\n\n");
theChecker++;
if(theChecker == 3)
theChecker -= 2;
}
printf("\nPress r to restart the game or any key to end the game: ");
scanf("%c", &answer);
printf("\n");
}
while(answer == 'r');
return 0;`enter code here`
}
Don't call srand() more than once, it's used to initialize the random seed, which you are always initializing to the same value, the internal state gets reset over and over, always producing the same pseudo-random values.
I say that you always pass the same seed, because time() has seconds resolution, and in once second, the whole game was played and terminated.
You just need a call to srand() at the beginning of the program to prevent the program from choosing the same values across runs of the program, not in the same run.

My program run and returns 0, but it doesn't display the cout data ive given it

When I Build and run my code it instantly returns 0 saying programing was successful, however i want it to display all the numbers from 100 to 200 that are divisible by 4.
Here's my code...
#include <iostream>
using namespace std;
int main()
{
int num = 200;
int snum;
cout<<"The following numbers are all divisble by 4 and are inbetween 100 and 200\n";
while(num<99)
{
snum = (num % 4) ;
cout<<snum<<endl;
cout<<num<<endl;
if(snum = 0)
{
cout<< num << endl;
}
else
{
}
num--;
}
return 0;
}
The while condition should be while (num > 99) instead of while(num<99)(false at the beginning)
The if condition should be if (snum == 0) instead of if(snum = 0)(= is assignment, not equal operator)
The else part has nothing, you may delete it. I added some other notes in the comments below.
while (num > 99)
{
snum = num % 4 ; // no need for the parenthesizes
if (snum == 0)
{
std::cout<< num << std::endl;
}
--num; //pre-increment is preferred, although doesn't matter in this case
}
Your loop never executes because the condition
(num<99)
is already false from the start. You probably meant
(num>99)
Also, the if statement condition
(snum = 0)
sets snum to zero, always returning zero, so you probably meant
(snum == 0)
You set num to be 200:
int num = 200;
Then you only run the loop if and when the number is less than 99:
while(num<99)
What do you expect will happen?
This is not how you do an equals-test in C:
if(snum = 0)
In C, equality is checked with ==:
if(snum == 0)
In fact, what you have (if (snum = 0)) will NEVER be true, so your if-statement will NEVER be executed.

C++ code for checking for prime numbers not working

I'm having trouble with this C++ code. The integer num is a number that I want to check if it is prime. However this program is always returning false. It's probably something simple but I can't find anything.
for(int i=2;i<num;i++){ //primes are allowed to be divided by 1 so we start at 2
if(num % i == 0){ //can be divided by a number other than itself or 1 so we trip out
return false;
} else if(i == num){ //if we've already done checks as high as possible and not tripped out yet then report success
return true;
}
}
i == num will never occur, since your loop condition is i<num. Try:
for(int i=2;i<num;i++){ //primes are allowed to be divided by 1 so we start at 2
if(num % i == 0){ //can be divided by a number other than itself or 1 so we trip out
return false;
} else if(i == num-1){ //if we've already done checks as high as possible and not tripped out yet then report success
return true;
}
}
As pointed out below, the else condition here is redundant, and you only need to check from 2 to sqrt(num) - since the remaining factors have already been checked.
There are more improvements that can be made depending on how complex you want to make the problem. Most methods in reality use probabilistic algorithms.
You don't have to check every number, as a lot of them can easily be ruled out. For example, after checking that num is not divisible by 2, you can skip all other even numbers. That saves you half the tests.
We also definitely know that any other factor must be less than num/2 (or really sqrt(num), but that is harder to compute). That knowledge can save us another half of the tests.
So now we have:
if (num % 2 == 0)
return false;
for(int i = 3; i < num / 2; i += 2){
if(num % i == 0){ //can be divided by a number other than itself or 1 so we trip out
return false;
}
}
// arriving here we have found no factors, so it must be a prime
return true;
A small optimization for Will Ness's code, just calculate the sqrt of the number outside the for. The condition check executes many times and has no sense to calculate sqrt each time.
if( num == 2 ) return true;
if( num < 2 || num % 2 == 0 ) return false;
int sqrt = sqrt(num);
for( int i=3; i<=sqrt; i+=2 ){
if(num % i == 0){
return false;
}
}
return true;
So far I think that this is the most efficient way!
bool CheckPrime(int num) {
bool yayornay = true;
for(int i = 2; i < num; i++) {
if(num % i == 0) {
yayornay = false;
break;
}
}
return yayornay;
}
bool isprime(int n)
{
if(n<2) return false;
if(n==2)return true;
for(int i=2;i<=sqrt(n);i++)
if(n%i==0) return false;
return true;
}
Here's the proper way to write what you meant:
int i=2; // move declaration out
for(/*int i=2*/;i<num;i++){
if(num % i == 0){
return false;
} // else // and the final test too
}
if(i == num){
return true;
}
But that's not efficient. You only have to check for i's not exceeding of sqrt(num). Plus, if you check num%2, there's no more need to check any other even numbers, so you can use an increment of 2. Or you can even count by 6:
if( num == 2 || num == 3 ) return true;
if( num < 2 || num % 2 == 0 || num % 3 == 0 ) return false;
for( int i=5, j=7, lim=sqrt(num); i<=lim; i+=6, j+=6 ){
if( num % i == 0 || num % j == 0 ){
return false;
}
}
return true;
(notice: this is more efficient than another answer here, which says it's an "optimization" of an initial version of this answer).