I heard that often "everything" besides 0 is true. But now very strange things are happening to me... or I just think that I do it in correct way while I don't. Here's what is happening:
When I want to check if a is equivalent b, I can use NOT(a XOR b). When I checked it for unsigned char's, everything was ok, for example
unsigned char a = 5;
unsigned char b = 3;
unsigned char c = ~(a^b);
gave me c == 249:
a is: 00000101, which is 5.
b is: 00000011, which is 3.
~(a^b) is: 11111001, which is 249.
Now, let's try this with bool's.
cout << ~(true^true) << ~(true^false) << ~(false^true) << ~(false^false) << endl;
cout << ~(~(true^true)) << ~(~(true^false)) << ~(~(false^true)) << ~(~(false^false)) << endl;
if (~(true^true) == true)
cout << "true";
else
cout << "false";
This gives me in console:
-1-2-2-1
0110
false
while I expected the first line to be:
1001
After asking a friend, he advised me to try ! instead of ~ and see if it will work correctly. And (I think) it works correctly now. But I don't understand why. Shouldn't boolean negation work for bools?
The ! (logical negation) operator determines whether the operand evaluates to 0 (false) or nonzero (true). The expression yields the value 1 (true) if the operand evaluates to 0, and yields the value 0 (false) if the operand evaluates to a nonzero value.
Zero is used to represent false, and One is used to represent true. For interpretation, Zero is interpreted as false and anything non-zero is interpreted as true. To make life easier, C Programmers typically define the terms "true" and "false" to have values 1 and 0 respectively.
The logical NOT ( ! ) operator (logical complement, negation) takes truth to falsity and vice versa. It is typically used with boolean (logical) values. When used with non-Boolean values, it returns false if its single operand can be converted to true ; otherwise, returns true .
Like in C, the integers 0 (false) and 1 (true—in fact any nonzero integer) are used.
You're misunderestimating the arithmetic conversions. When you say ~e for some expression e of integral type, the value is first promoted to at-least-int, and same for e1 ^ e2 (and for any arithmetic expressions, for that matter). So true ^ true first has its operands promoted to int, yielding 1 ^ 1, which is indeed 0, and thus you end up with ~0, which on your platform is -1.
You can vaguely make sense of your operation by converting the result back to bool:
std::cout << static_cast<bool>(~(true ^ true))
In your final problem, since you have an expression with the == operator where the two operands have different types, both operands are promoted to the common type, which is again int, and -1 is different from 1. Again, you can convert both operands to bool first to get the desired equality.
The meta lesson is that the built-in operators in C++ acting on integers really only operate on int and wider, but not on any of the shorter types (bool, char, short) (and similar considerations apply to passing integers through an ellipsis). While this may cause some confusion at times, it also simplifies the language rules a bit, I suppose. This is all part of the C heritage of C++.
I heard that often "everything" besides 0 is true
It is valid for conditions as for example in the if statement (here and below I am citing the C++Standard)
The value of a condition that is an expression is the value of the expression, contextually converted to bool for statements other than switch
For example if you would write as
if (~(true^true) )
cout << "true";
else
cout << "false";
instead of your code snippet
if (~(true^true) == true)
cout << "true";
else
cout << "false";
or when the logical negation operator ! is used
9 The operand of the logical negation operator ! is contextually converted to bool (Clause 4); its value is true if the converted operand is false and false otherwise. The type of the result is bool
As for operator == then
6 If both operands are of arithmetic or enumeration type, the usual arithmetic conversions are performed on both operands; each of the operators shall yield true if the specified relationship is true and false if it is false.
That is in case of
if (~(true^true) == true)
the usual arithmetic conversion is applied that is boolean value true is converted to integer value 1 and it is not equal to the expression of the left operanf because internal binary representation of the left operand differs from 1 as showed the output of your first code snippet..
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With