How to combine two if statements into one - c++

Hi I have these two separate if statements, when put like so ;
if (powerlevel <= 0) // <--- ends up having no effect
if (src.health <= 0)
the_thing_to_do();
How do I combine these two if statements into one? is it possible? If so how?

If you want both statements to be true use logical AND
if(powerlevel <= 0 && src.health <= 0)
If you want either of the statements to be true use logical OR
if(powerlevel <= 0 || src.health <= 0)
Both of the above operators are logical operators

Use operator&& if you want both of them to be met (logical AND)
if(powerlevel <= 0 && src.health <= 0) { .. }
or operator|| if you want just one to be met (logical OR)
if(powerlevel <= 0 || src.health <= 0) { .. }

It depends if you want both to evaluate to true...
if ((powerlevel <= 0) && (src.health <= 0)) {
// do stuff
}
... or at least one ...
if ((powerlevel <= 0) || (src.health <= 0)) {
// do stuff
}
The difference being logical AND (&&) or logical OR (||)

Just an aternative if it is meaningful(sometimes).
Both true:
if (!(src.health > 0 || powerlevel > 0)) {}
at least one is true:
if (!(src.health > 0 && powerlevel > 0)) {}

Or if you don't want to use && you can use a Ternary Operator
#include <iostream>
int main (int argc, char* argv[])
{
struct
{
int health;
} src;
int powerlevel = 1;
src.health = 1;
bool result((powerlevel <= 0) ? ((src.health <=0) ? true : false) : false);
std::cout << "Result: " << result << std::endl;
}

Related

How to Rewrite "IF CONDITION " for ON for 3min and OFF for 10min until 4Hr (240min)

I want shorten the if condition. How can I simplify this?
Where step = 1 to 240 in min
I want 1st 3 min ON= 1, second 10 min OFF = 0, It will repeated until 248 min
I wrote "if condition" which is consist of many condition. How to rewrite the code with simple expression
#include "udf.h"
DEFINE_PROFILE(ON_3min_OFF_10min_4Hr,thread,position)
{
face_t f;
real step,hf_3min,hf_10min;
hf_3min = 1; /*ON */
hf_10min = 0; /*OFF */
step=N_TIME;
begin_f_loop(f,thread)
{
if ((step<=3) || ((step>13) && (step<=16)) || ((step>26) && (step<=29)) || ((step>39) && (step<=42)) || ((step>52) && (step<=55)) || ((step>65) && (step<=68)) || ((step>78) && (step<=81)) || ((step>91) && (step<=94)) || ((step>104) && (step<=107)) || ((step>117) && (step<=120)) || ((step>130) && (step<=133)) || ((step>143) && (step<=146)) || ((step>156) && (step<=159)) || ((step>169) && (step<=172)) || ((step>182) && (step<=185)) || ((step>195) && (step<=198)) || ((step>208) && (step<=211)) || ((step>222) && (step<=225)) || ((step>235) && (step<=238)))
{
F_PROFILE(f,thread,position)=hf_3min;
}
else
{
F_PROFILE(f,thread,position)=hf_10min;
}
}
end_f_loop(f,thread)
}
From the bounds that you are checking, it seems your code is equivalent to:
if ((step - 1) % 13 < 3) {
F_PROFILE(f, thread, position) = hf;
} else {
F_PROFILE(f, thread, position) = hf2;
}
You need to be careful about the missing lower bound on the first condition, and the change of the bounds at the last 2 conditions, in case that's intentional.

Issues with commutative property of && operator

The code below that I have been having strange issues with is meant to trim off the unused portion of an integer array, and then convert it into a string.
Ex:
_ABC__DE______ would become _ABC__DE.
The problems show up when the input is filled with the default character. ("_" in the example).
sLength is the length of the integer array chars
The problematic code:
int inputLength = sLength - 1;
while (chars[inputLength] == defaultChar && inputLength >= 0) {
inputLength--;
}
inputLength++;
Serial.println("input length: " + String(inputLength));
// (in)sanity check
Serial.println(inputLength);
Serial.println(String(inputLength));
Serial.println(inputLength <= 0);
Serial.println(0 <= 0);
Serial.println(inputLength == 0);
Serial.println(0 == 0);
if (inputLength <= 0) {
//reset cursor position
Serial.println("index set to 0");
index = 0;
} else {
output = "";
for (int i = 0; i < inputLength; i++) {
char c = charSet[chars[i]];
if (c == '_') {
c = ' ';
}
output += c;
}
done = true;
}
The output when given an array filled with defaultChar:
input length: 0
0
0
0
1
0
1
If I'm interpreting correctly, the output means that 0 > 0 and 0 =/= 0 on even lines, but 0 <= 0 and 0 = 0 on odd lines.
The workaround I've come up with is replacing
while (chars[inputLength] == defaultChar && inputLength >= 0) {
inputLength--;
}
with one of the following
while (inputLength >= 0 && chars[inputLength] == defaultChar) {
inputLength--;
}
.
while (chars[inputLength] == defaultChar) {
inputLength--;
if (inputLength < 0) {
break;
}
}
which both result in an output of:
input length: 0
0
0
1
1
1
1
index set to 0
Why does this change the result?
As far as I knew until now, the && operator was commutative.
Is there something that I am missing that makes
chars[inputLength] == defaultChar && inputLength >= 0
not equal to
inputLength >= 0 && chars[inputLength] == defaultChar?
If It's relevant, this is being run on an 328P Arduino Nano with the old bootloader using IDE 1.8.8
&& is not commutative. It evaluates the left operand first and then stops if the left operand evaluated to 0.
Your original code fails because at some point it evaluates chars[-1] (which causes undefined behaviour if chars is an array). The alternative version does not have that problem because it performs the >= 0 test before using inputLength as an array index.
&& is commutative in the sense that the result of a && b is same as the result of b && a. But the built-in operator && has a short-circuiting behavior. This means that if the result of a && b can be decided by evaluating the first operand alone, the second one is not evaluated.
So when the first operand is chars[inputLength] == defaultChar and inputLength is -1, you enter the territory of undefined behavior which means the behavior of the program is unpredictable. But with the workarounds, you avoid undefined behavior because of the inputLength >= 0 and inputLength < 0 checks and therefore the code works as intended.
As #PeteBecker notes: a() && b() is not commutative if either a() or b() has side effects.

Logical OR precedence

I have tried writing a loop that would refrain the user to enter a wrong kind of data (actually a boolean) into the program by using the || operator.
int Entrer()
{
int A;
do
{
cout<<"Entrez 0 ou 1."<<endl;
cin >> A;
}
while (A != (1 || 0));
return A;
}
Can somebody tell me why the program only accepts 1 and no 0 ?
do { ... } while (A != (1 || 0));
It should be while (A != 1 && A != 0);
Otherwise, A != (1 || 0) stands for A != 1 since (1 || 0) is evaluated before !=.
If you want to accept 1 and 0, you need to write the conditional as while(A != 1 && A != 0);. As your conditional written, it will evaluate the (1 || 0) first, and, as 1 is true and 0 is false, will evaluate to A != 1.

Check if C-style array equals other (compile-time) array

I've got a double[9] and want to check if it contains the values (1,0,0,0,1,0,0,0,1). Is there a cleaner way than this?
if (ornt1[0] == 1 && ornt1[1] == 0 && ornt1[2] == 0
&& ornt1[3] == 0 && ornt1[4] == 1 && ornt1[5] == 0
&& ornt1[6] == 0 && ornt1[7] == 0 && ornt1[8] == 1 )
I'm using C++.
It is not a good idea to compare double values strictly. I would recommend you create a constant array to compare against and then use a cycle and also use a tolerance(e.g. 1e-9):
bool doublesEqual(double a, double b) {
return fabs(a - b) < 1e-9;
}
const double expected[9] = {1,0,0,0,1, 0, 0, 0, 1};
bool equal = true;
for (int i = 0; i< 9; ++i) {
if (!doublesEqual(expected[i], ornt1[i])) {
equal = false;
break;
}
}
if (equal) { // do smth
EDIT: as suggested by John Zwinck I have edited the code to be able to handle the case when the array we compare contains only NAN. I have edited his suggestion a bit to make the code more readable. Please refer to his comment below for clarification why this is needed.

bool operation in expression

#include <iostream.h>
int main() {
int choice;
cin>>choice;
if (1<=choice<=3) cout<<"good";
else cout<<"bad";
return 0;
}
How is the bool expression is evaluated? is this expression equal to
if ((1<=choice)||(choice<=3))
if (1<=choice<=3) cout<<"good";
Is like writing:
if ((1<=choice)<=3) cout<<"good";
Which is always satisfied because 1<=choice returns 0 or 1 (0 is false and 1 is true), which is always <=3.
What you (probably) want to do is:
if(1 <= choice && choice <=3)
(1<=choice<=3)
is not equivalent to:
(1 <= choice || choice <= 3)
but rather:
((1 <= choice) <= 3)
Which is always going to be true, since int(1 <= choice) is equal to 0 or 1
I assume that what you want is:
(1 <= choice && choice <= 3)
You need this.
if (1<=choice && choice <=3) cout<<"good";