Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does ~True result in -2?

In Python console:

~True

Gives me:

-2

Why? Can someone explain this particular case to me in binary?

like image 849
lukaszkups Avatar asked Feb 19 '14 13:02

lukaszkups


People also ask

What test strips work with true result meter?

The TRUEresult® and TRUE2go® blood glucose systems use TRUEtest test strips, which are GDH-PQQ enzyme-based test strips. For a very small percentage of the population with diabetes, the GDH-PQQ enzyme can interfere with certain drug products or therapies that contain non-glucose sugars.


3 Answers

int(True) is 1.

1 is:

00000001

and ~1 is:

11111110

Which is -2 in Two's complement1

1 Flip all the bits, add 1 to the resulting number and interpret the result as a binary representation of the magnitude and add a negative sign (since the number begins with 1):

11111110 → 00000001 → 00000010 
         ↑          ↑ 
       Flip       Add 1

Which is 2, but the sign is negative since the MSB is 1.


Worth mentioning:

Think about bool, you'll find that it's numeric in nature - It has two values, True and False, and they are just "customized" versions of the integers 1 and 0 that only print themselves differently. They are subclasses of the integer type int.

So they behave exactly as 1 and 0, except that bool redefines str and repr to display them differently.

>>> type(True)
<class 'bool'>
>>> isinstance(True, int)
True

>>> True == 1
True
>>> True is 1  # they're still different objects
False
like image 79
Maroun Avatar answered Oct 23 '22 18:10

Maroun


The Python bool type is a subclass of int (for historical reasons; booleans were only added in Python 2.3).

Since int(True) is 1, ~True is ~1 is -2.

See PEP 285 for why bool is a subclass of int.

If you wanted the boolean inverse, use not:

>>> not True
False
>>> not False
True

If you wanted to know why ~1 is -2, it's because you are inverting all bits in a signed integer; 00000001 becomes 1111110 which in a signed integer is a negative number, see Two's complement:

>>> # Python 3
...
>>> import struct
>>> format(struct.pack('b', 1)[0], '08b')
'00000001'
>>> format(struct.pack('b', ~1)[0], '08b')
'11111110'

where the initial 1 bit means the value is negative, and the rest of the bits encode the inverse of the positive number minus one.

like image 43
Martijn Pieters Avatar answered Oct 23 '22 18:10

Martijn Pieters


~True == -2 is not surprising if True means 1 and ~ means bitwise inversion...

...provided that

  • True can be treated as an integer and
  • integers are represented in Two's complement

Edits:

  • fixed the mixing between integer representation and bitwise inversion operator
  • applied another polishing (the shorter the message, the more work needed)
like image 44
Wolf Avatar answered Oct 23 '22 18:10

Wolf