I've done the LinkedIn C++ Assessment and got the following question:
What is the result from executing this code snippet?
bool x=true, x=false;
if(~x || y) {
/*part A*/
}
else {
/*part B*/
}
I don't know anymore what the answers were, but I thought "B" should be displayed, right?
I thought by "~", x is inverted ("bitwise NOT") and is therefore no longer "true"
But when I run the code, I get "A":
Code:
#include <iostream>
int main()
{
bool x = true, y = false;
std::cout << "x: " << x << std::endl;
std::cout << "~x: " << ~x << std::endl;
if (~x || y) {
std::cout << "A" << std::endl;
}
else {
std::cout << "B" << std::endl;
}
return 0;
}
Output:
x: 1
~x: -2
A
Can someone explain this to me?
In this expression
~x
there is applied the integral promotions to the operand x of the type bool. The result of the promotion is an object of the type int
that has the value equal to 1 like (in binary)
00000000 00000000 00000000 00000001
The operator ~ inverses bits and you will get
11111111 11111111 11111111 11111110
From the C++ 14 Standard (5.3.1 Unary operators)
10 The operand of ~ shall have integral or unscoped enumeration type; the result is the one’s complement of its operand. Integral promotions are performed. The type of the result is the type of the promoted operand.
and (4.5 Integral promotions)
6 A prvalue of type bool can be converted to a prvalue of type int, with false becoming zero and true becoming one.
7 These conversions are called integral promotions.
As this value is not equal to 0 then used as an operand of the logical OR operator it is implicitly converted to the boolean value true.
From the C Standard (5.15 Logical OR operator)
1 The || operator groups left-to-right. The operands are both contextually converted to bool (Clause 4). It returns true if either of its operands is true, and false otherwise. Unlike |, || guarantees left-to-right evaluation; moreover, the second operand is not evaluated if the first operand evaluates to true.
and (4.12 Boolean conversions)
1 A prvalue of arithmetic, unscoped enumeration, pointer, or pointer to member type can be converted to a prvalue of type bool. A zero value, null pointer value, or null member pointer value is converted to false; any other value is converted to true. For direct-initialization (8.5), a prvalue of type std::nullptr_t can be converted to a prvalue of type bool; the resulting value is false.