Meaning of a comparator statement in C++ - c++

I am reading this code in C++
http://ajmarin.alwaysdata.net/codes/problems/952/ and I don't understand what this &= in the code does:
int k = 5;
int ts = 5;
bool possible = true;
And it have this line:
if(!(possible &= k == ts))
break;
I want to know what is the meaning of "&=" I am new in C++ language and I've never seen something like this for example in java, or at least I don't know the meaning.
The right hand of the statement returns "1" due to the fact that ( k == ts ) that is ( 5 == 5) but the left hand ( possible &= k ) don't know the meaning..
Thank you

It's equivalent to:
possible &= (k == ts);
if (! possible)
and is further equivalent to
possible = possible & (k == ts);
if (! possible)
Here, & is the bitwise AND. num & 0 will always gives you 0 while num & 1 will give you 1 if the least significant bit of num is 1 or 0 otherwise.
To read on, check out
Bitwise AND Assignment Operator (&=)
C++ Operator Precedence

It is a bitwise-AND-assignment, which is a Compound Assignment Operator. It is equivalent to the following statement:
possible = possible & (k == ts);
if(!possible)
....
Note that your original code-style is considered by many to be an anti-pattern, and you should in general avoid assignments in if statements (e.g. here and here).

&= is Bitwise AND assigning the result to the lhs( a&=b => a=a&b). (like +=)
It will perform a logical AND and assign the result to possible.
Due to Operator precedence the expression will be like: possible &= (k == ts).
Which means that it will evaulate (k == ts) resulting in a boolean, make a logical and with possible, store it in possible and return it as a result.

Related

What happens due to & operator in the following case?

I have known, '&' as bitwise and as an operator to get memory address of a variable.
What happens in this case of the code?
res = res & (a[i]<[a[i+1]]);
If it is bitwise and , as far as I know the second condition is also checked,
but what if I used logical and instead of it , wouldn't it still be the same?
As first part is (say) false , second parts get checked comes true, but still res remains false.
Would it be same (for this case) to use logical and for this? or it has some other use (& operator) for this case?
int a[] {1,3,4,2};
int pos = 3;
bool res = true;
for(int i = 0; i < pos; i++)
res &= (a[i] < a[i + 1]);
(Sorry for bad english)
If it is bitwise and , as far as I know the second condition is also checked, but what if I used logical and instead of it , wouldn't it still be the same?
No. Boolean and (written as && or and) has short circuit evaluation - if left part is false right part is not evaluated at all. This allows to write code like this:
if( pointer != nullptr && pointer->value > 100 ) ...
if not short circuit evaluation this code would have UB. For example this code:
if( pointer != nullptr & pointer->value > 100 ) ...
has Undefined Behaviour when pointer is equal to nullptr
Would it be same (for this case) to use logical and for this? or it has some other use (& operator) for this case?
You cannot, as there is no &&= operator in C++. You can write:
res = res && (a[i] < a[i + 1]);
and that would have short circuit as well and compiler may even be smart enough to stop the loop, though I doubt and it should be expressed explicitly anyway:
bool res = true;
for(int i = 0; res && i < pos; i++)
res = a[i] < a[i + 1];
which does the same, but cleaner and more efficient.
Anyway when you need logical or boolean and you should use one to make your intention clear and avoid unexpected surprises.
Besides the short circuiting issue, If res == 2 then:
res & 1 will return 0 which will be interpreted as false.
res && 1 will return true.
Your question is not clear.
Okay, let's dive into your code.
Your given code is very clear. You are performing bitwise and for pos(3) times. For every loop you are comparing a[i] with a[i+1]. Please note that for the last loop, I mean when variable i becomes 3, then i+1 will be 4. And your array a[] doesn't have a[4]. It only has the last element having index 3.
So for bitwise and operation the value of res isn't predictable as a[4] isn't defined.
Now let's think about logical AND operation. For logical and your expression inside the for loop will once generate a false boolean value for a[i] < a[i+1] as your array a[] = {1,3,4,2}. Here 4>2 not 4<2. Hence it will generate false boolean value and your entire response will be false 'cause you know logical AND will be eventually 0 if one of the operands is false.
I think you have got this.

C++ multiple operators: assign A or B not equal to C

I am currently learning from an SDL2/OpenGL2 example code, for ImGui. Then, I ran into a line (and a few more alike) as shown below. I believe this part binds SDL mouse events to IMGUI API. However, I do not quite understand how it works.
io.MouseDown[0] = g_MousePressed[0] || (mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT)) != 0
where,
ImGuiIO& io = ImGui::GetIO();
bool mouseDown[5]; // a member of ImGuiIO struct
static bool g_MousePressed[3] = { false, false, false };
Uint32 mouseMask = SDL_GetMouseState(&mx, &my);
(I hope above is enough information...)
What makes me the most confused is the the last part, not equal to 0. I could understand it, if it was a simple assignment of the result of an And and an Or operations. However, there is not equal to zero following at the end and I have not seen this before. I would like to get some help to understand this code please.
expression != 0
is a boolean expression and thus evaluates to either true or false which can be converted to integer values of 0 or 1.
#include <iostream>
int main() {
constexpr size_t SDL_BUTTON = 5;
for (size_t mouseMask = 0; mouseMask < 16; ++mouseMask) {
std::cout << mouseMask << ' '
<< (mouseMask & SDL_BUTTON) << ' '
<< ((mouseMask & SDL_BUTTON) != 0) << '\n';
}
}
Live demo: http://ideone.com/jcmosg
Since || is the logical or operator, we are performing a logical comparison that tests whether io.MouseDown != 0 or (mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT)) != 0 and yields a boolean value (true or false) promoted to whatever type io.mouseDown[0] is.
The code could actually have been written as:
io.MouseDown[0] = g_MousePressed[0] || (mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT))
or
const bool wasPressed = g_mousePressed[0];
const bool newPress = mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT);
const either = (wasPressed == true) || (newPress == true);
io.MouseDown[0] = either;
or
if (g_mousePressed[0])
io.MouseDown[0] = 1;
else if (mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT))
io.MouseDown[0] = 1;
else
io.MouseDown[0] = 0;
See http://ideone.com/TAadn2
If you are intending to learn, find yourself a good sandbox (an empty project file or an online ide like ideone.com etc) and teach yourself to experiment with pieces of code you don't immediately understand.
An expression a = b || c!=0 means a = (b!=0) || (c!=0). In boolean logic, b and b!=0 are equivalent. That's what I think the most confusing part. Once this is understood, there should be no problem.
Note that this expression should not be confused with a=b|c!=0, where | is a binary operation called "bit-wise or", as opposed to the logical operation ||, which is the logical "or". When doing b|c!=0, c!=0 is calculated first to yield a logical value 0 or 1, then b|0 or b|1 is calculated to do nothing (first case) or reset the last bit of the binary code of b to 1 (second case). Finally, that result is assigned to a. In this case, b and b!=0 are not equivalent, because the bit-wise or | is used instead of the logical or ||.
Similarly, & is the "bit-wise and" operator, while && is the logical "and". These two should not be confused either.
Notice that != has a higher precedence than ||, so the whole expression is indeed a simple assignment of the result of an OR.
The !=0 part is a way to turn the result of applying a bitmask into bool, as #AlekDepler said. Funny thing is its pretty much redundant (if mouseMask is of built-in integral type) as implicit conversion from say int to bool works exactly like !=0.

Understanding "Bitwise-And (&)" and "Unary complement(~)" in c++

I have some trouble understanding Bitwise-And and Unary Complement when both are used in this code snippet
if((oldByte==m_DLE) & (newByte==m_STX)) {
int data_index=0;
//This below line --- does it returns true if both the oldByte and newByte are not true
//and within timeout
while((timeout.read_s()<m_timeout) & ~((oldByte==m_DLE) & (newByte==m_ETX))) {
if(Serial.available()>0) {
oldByte=newByte;
newByte=Serial.read();
if(newByte==m_DLE) {
.
.
.
are the both operators & ~are performing a logical not operation like checking until if both oldByte and newByte are false
The above code is from the link --> line 227 of the code
I am trying to use the implement the code for my application in C but without the timing functions
if((oldByte==DLE) && (newByte== STX)) {
data_index = 0;
// is this the correct implematation for above C++ code to C
while(! ((oldByte== DLE) && (newByte== ETX))){
oldByte = newByte;
Is this method correct for implementing in C
(timeout.read_s()<m_timeout) & ~((oldByte==m_DLE) & (newByte==m_ETX))
is equivalent to (but probably less readable than)
(timeout.read_s()<m_timeout) && !(oldByte==m_DLE && newByte==m_ETX)
which is equivalent to (and IMO less readable than)
(timeout.read_s()<m_timeout) && (oldByte!=m_DLE || newByte!=m_ETX)
Edit: should add a caveat about short-circuiting. Although the particular example statements will all return the same value, using && or || will skip evaluating pieces that can't impact the result. This isn't important in your specific example, but could be very important in an example like this:
(oldByte!=nullptr & *oldByte == m_ETX) // will crash when oldByte=nullptr.
(oldByte!=nullptr && *oldByte == m_ETX) // will evaluate to false when oldByte=nullptr.
Since the equality-operator (==) yields 0 or 1 as a result, you can use bitwise and, too. (foo==1) & ~(bar==1) works too, since the AND with (foo==1), which always results in 1 and 0, masks all other bits in ~(bar==1). However, it is strongly recommended to use the logical counterparts &&, || and !.
The following would not work as expected:
if (~(bar == 1) & ~(foo == 1))
e.g. if foo = bar = 1, then it would evaluate to 0xfffffffe on ia32, which is different from 0 and therefore "TRUE"

Operator Precedence

I have a sample midterm question that I am not too sure about. Here it is:
#include <iostream.h>
void f( int i )
{
if( i = 4 || i = 5 ) return;
cout << "hello world\n" ;
}
int main()
{
f( 3 );
f( 4 );
f( 5 );
return 0;
}
So I understand that the logical OR operator has a higher precedence and that it is read left to right. I also understand that what's being used is an assignment operator instead of the relational operator. I just dont get how to make sense of it all. The first thing the compiler would check would be 4 || i? How is that evaluated and what happens after that?
Let's add all the implied parentheses (remembering that || has higher precedence than = and that = is right-associative):
i = ((4 || i) = 5)
So, it first evaluates 4 || i, which evaluates to true (actually, it even ignores i, since 4 is true and || short-circuits). It then tries to assign 5 to this, which errors out.
As written, the code doesn't compile, since operator precedence means it's i = ((4 || i) = 5) or something, and you can't assign to a temporary value like (4 || i).
If the operations are supposed to be assignment = rather than comparison == for some reason, and the assignment expressions are supposed to be the operands of ||, then you'd need parentheses
(i = 4) || (i = 5)
As you say, the result of i=4 is 4 (or, more exactly, an lvalue referring to i, which now has the value 4). That's used in a boolean context, so it's converted to bool by comparing it with zero: zero would become false, and any other value becomes true.
Since the first operand of || is true, the second isn't evaluated, and the overall result is true. So i is left with the value 4, then the function returns. The program won't print anything, whatever values you pass to the function.
It would make rather more sense using comparison operations
i == 4 || i == 5
meaning the function would only print something when the argument is neither 4 nor 5; so it would just print once in your example, for f(3).
Note that <iostream.h> hasn't been a standard header for decades. You're being taught an obsolete version of the language, using some extremely dubious code. You should get yourself a good book and stop wasting time on this course.
The compiler shall isuue an error because expression 4 || i is not a lvalue and may not be assigned.
As for the expression itself then the value of it is always equal to true because 4 is not equal to zero.

Simplify this expression

Let a, b be positive integers with different values. Is there any way to simplify these expressions:
bool foo(unsigned a, unsigned b)
{
if (a % 2 == 0)
return (b % 2) ^ (a < b); // Should I write "!=" instead of "^" ?
else
return ! ( (b % 2) ^ (a < b) ); // Should I write "(b % 2) == (a < b)"?
}
I am interpreting the returned value as a boolean.
How is it different from
(a%2)^(b%2)^(a<b)
which in turn is
((a^b)&1)^(a<b)
or, indeed
((a ^ b) & 1) != (a < b)
Edited to add: Thinking about it some more, this is just the xor of the first and last bits of (a-b) (if you use 2's complement), so there is probably a machine-specific ASM sequence which is faster, involving a rotate instruction.
As a rule of thumb, don't mix operators of different operator families. You are mixing relational/boolean operators with bitwise operators, and regular arithmetic.
This is what I think you are trying to do, I'm not sure, since I don't understand the purpose of your code: it is neither readable nor self-explaining.
bool result;
bool a_is_even = (a % 2) == 0;
bool b_is_even = (b % 2) == 0;
if (a_is_even == b_is_even) // both even or both odd
result = a < b;
else
result = a >= b;
return result;
I program in C# but I'd think about something like this:
return (a % 2 == 0) && ((b % 2) ^ (a < b))
Considering from you comments that '^' is equivalent to '=='
If you are returning a truth value, a boolean, then your proposed changes do not change the semantics of the code. That's because bitwise XOR, when used in a truth context, is the same as !=.
In my view your proposed changes make the code much easier to understand. Quite why the author thought bitwise XOR would be appropriate eludes me. I guess some people think that sort of coding is clever. I don't.
If you want to know the relative performance of the two versions, write a program and time the difference. I'd be surprised if you could measure any difference between them. And I'd be equally surprised if these lines of code were your performance bottleneck.
Since there is not much information around this issue, try this:
int temp = (b % 2) ^ (a < b);
if (a % 2 == 0)
return temp;
else
return !temp;
This should be less code if the compiler hasn't optimized it already.