Bitwise operators in Python (AND, OR, XOR, NOT, SHIFT)
Python provides the bitwise operators, &
(AND), |
(OR), ^
(XOR), ~
(NOT, invert), <<
(LEFT SHIFT), >>
(RIGHT SHIFT).
For more information about converting binary, octal, and hexadecimal numbers and strings using bin()
, oct()
, hex()
, and format()
, see the following articles.
See the following article on how to count the number of 1
s in binary representation for integer int
.
For Boolean operations on bool
types (True
, False
) instead of bitwise operations, see the following article. Use and
and or
instead of &
and |
.
Inputs and outputs for AND, OR, and XOR
The inputs and outputs for each bit of AND, OR, and XOR are as follows.
Input 1 | Input 2 | AND | OR | XOR |
---|---|---|---|---|
1 | 1 | 1 | 1 | 0 |
1 | 0 | 0 | 1 | 1 |
0 | 1 | 0 | 1 | 1 |
0 | 0 | 0 | 0 | 0 |
Bitwise AND: &
Bitwise AND with the &
operator:
x = 12 # 0b1100
y = 10 # 0b1010
print(x & y)
print(bin(x & y))
# 8
# 0b1000
Bitwise OR: |
Bitwise OR with the |
operator:
x = 12 # 0b1100
y = 10 # 0b1010
print(x | y)
print(bin(x | y))
# 14
# 0b1110
Bitwise XOR: ^
Bitwise XOR with the ^
operator:
x = 12 # 0b1100
y = 10 # 0b1010
print(x ^ y)
print(bin(x ^ y))
# 6
# 0b110
Bitwise operations with negative integers
Bitwise operations on negative integers are handled as if the values were expressed in two's complement.
Note that converting a negative integer to a binary string using bin()
or format()
results in a minus sign rather than the two's complement format.
x = -9
print(x)
print(bin(x))
# -9
# -0b1001
To get a string expressed in two's complement representation, perform the bitwise AND &
with the maximum number of digits required. For example, use 0b1111
(= 0xF
) for 4-bit, 0xFF
for 8-bit, and 0xFFFF
for 16-bit.
print(bin(x & 0xFF))
print(format(x & 0xFF, 'b'))
# 0b11110111
# 11110111
Keep in mind that leading zeros are omitted unless zero-padding is specified.
print(bin(x & 0b1111))
print(format(x & 0b1111, 'b'))
# 0b111
# 111
print(format(x & 0b1111, '#06b'))
print(format(x & 0b1111, '04b'))
# 0b0111
# 0111
Bitwise NOT, invert: ~
The ~
operator yields the bitwise inversion. The bitwise inversion of x
is defined as -(x+1)
.
If the input value x
is regarded as two's complement and all bits are inverted, the result is equivalent to -(x+1)
.
Converting ~x
to a string does not yield a string with the bits of the original value inverted.
x = 9 # 0b1001
print(~x)
print(bin(~x))
# -10
# -0b1010
By applying the AND operation to create a string in two's complement representation, you can obtain a string with the inverted bits. For example, to get a 4-digit bit inverted string, specify '04b'
with format()
and pad it with zeros.
print(bin(~x & 0xFF))
print(format(~x & 0b1111, '04b'))
# 0b11110110
# 0110
Bit shifts: <<
, >>
Left shift and right shift with operators <<
, >>
:
x = 9 # 0b1001
print(x << 1)
print(bin(x << 1))
# 18
# 0b10010
print(x >> 1)
print(bin(x >> 1))
# 4
# 0b100
For negative values, the sign bit is extended and shifted, and negative values are treated as having an infinite number of ones on the left side.
x = -9
print(bin(x))
print(bin(x & 0xFF))
# -0b1001
# 0b11110111
print(x << 1)
print(bin(x << 1))
print(bin((x << 1) & 0xFF))
# -18
# -0b10010
# 0b11101110
print(x >> 1)
print(bin(x >> 1))
print(bin((x >> 1) & 0xFF))
# -5
# -0b101
# 0b11111011
Understanding bit shifts for negative values as numerical values can be challenging; it's more intuitive to consider them as two's complement strings.