What does |= (ior) do in Python?

Question:

Google won’t let me search |= so I’m having trouble finding relevant documentation. Anybody know?

Asked By: Sean W.

||

Answers:

In Python, and many other programming languages, | is the bitwise-OR operation. |= is to | as += is to +, i.e. a combination of operation and asignment.

So var |= value is short for var = var | value.

A common use case is to merge two sets:

>>> a = {1,2}; a |= {3,4}; print(a)
{1, 2, 3, 4}
Answered By: Daniel Stutzbach

It performs a binary bitwise OR of the left-hand and right-hand sides of the assignment, then stores the result in the left-hand variable.

http://docs.python.org/reference/expressions.html#binary-bitwise-operations

Answered By: Brandon Rhodes

This is just an OR operation between the current variable and the other one. Being T=True and F=False, see the output graphically:

r s r|=s
T T T
T F T
F T T
F F F

For example:

>>> r=True
>>> r|=False
>>> r
True
>>> r=False
>>> r|=False
>>> r
False
>>> r|=True
>>> r
True
Answered By: fedorqui

When used with sets it performs union operation.

Answered By: Kondalarao V

|= performs an in-place+ operation between pairs of objects. In particular, between:

In most cases, it is related to the | operator. See examples below.

Sets

For example, the union of two sets assigned to s1 and s2 share the following equivalent expressions:

>>> s1 = s1 | s2                                           # 1
>>> s1 |= s2                                               # 2
>>> s1.__ior__(s2)                                         # 3

where the final value of s1 is equivalent either by:

  1. an assigned OR operation
  2. an in-place OR operation
  3. an in-place OR operation via special method++

Example

Here we apply OR (|) and the in-place OR (|=) to sets:

>>> s1 = {"a", "b", "c"}
>>> s2 = {"d", "e", "f"}

>>> # OR, | 
>>> s1 | s2
{'a', 'b', 'c', 'd', 'e', 'f'}
>>> s1                                                     # `s1` is unchanged
{'a', 'b', 'c'}

>>> # In-place OR, |=
>>> s1 |= s2
>>> s1                                                     # `s1` is reassigned
{'a', 'b', 'c', 'd', 'e', 'f'}

Dictionaries

In Python 3.9+, new merge (|) and update (|=) operators are proposed between dictionaries. Note: these are not the same as set operators mentioned above.

Given operations between two dicts assigned to d1 and d2:

>>> d1 = d1 | d2                                           # 1
>>> d1 |= d2                                               # 2

where d1 is equivalent via:

  1. an assigned merge-right operation
  2. an in-place merge-right (update) operation; equivalent to d1.update(d2)

Example

Here we apply merge (|) and update (|=) to dicts:

>>> d1 = {"a": 0, "b": 1, "c": 2}
>>> d2 = {"c": 20, "d": 30}

>>> # Merge, | 
>>> d1 | d2
{"a": 0, "b": 1, "c": 20, "d": 30}
>>> d1 
{"a": 0, "b": 1, "c": 2}

>>> # Update, |=
>>> d1 |= d2
>>> d1 
{"a": 0, "b": 1, "c": 20, "d": 30}

Counters

The collections.Counter is related to a mathematical datastructure called a multiset (mset). It is basically a dict of (object, multiplicity) key-value pairs.

Given operations between two counters assigned to c1 and c2:

>>> c1 = c1 | c2                                           # 1
>>> c1 |= c2                                               # 2

where c1 is equivalent via:

  1. an assigned union operation
  2. an in-place union operation

A union of multisets contains the maximum multiplicities per entry. Note, this does not behave the same way as between two sets or between two regular dicts.

Example

Here we apply union (|) and the in-place union (|=) to Counters:

import collections as ct


>>> c1 = ct.Counter({2: 2, 3: 3})
>>> c2 = ct.Counter({1: 1, 3: 5})

>>> # Union, |    
>>> c1 | c2
Counter({2: 2, 3: 5, 1: 1})
>>> c1
Counter({2: 2, 3: 3})

>>> # In-place Union, |=
>>> c1 |= c2
>>> c1
Counter({2: 2, 3: 5, 1: 1})

Numbers

Lastly, you can do binary math.

Given operations between two numbers assigned to n1 and n2:

>>> n1 = n1 | n2                                           # 1
>>> n1 |= n2                                               # 2

where n1 is equivalent via:

  1. an assigned bitwise OR operation
  2. an in-place bitwise OR operation

Example

Here we apply bitwise OR (|) and the in-place bitwise OR (|=) to numbers:

>>> n1 = 0
>>> n2 = 1

>>> # Bitwise OR, |
>>> n1 | n2
1
>>> n1
0

>>> # In-place Bitwise OR, |=
>>> n1 |= n2
>>> n1
1

Review

This section briefly reviews some bitwise math. In the simplest case, the bitwise OR operation compares two binary bits. It will always return 1 except when both bits are 0.

>>> assert 1 == (1 | 1) == (1 | 0) == (0 | 1)
>>> assert 0 == (0 | 0)

We now extend this idea beyond binary numbers. Given any two integral numbers (lacking fractional components), we apply the bitwise OR and get an integral result:

>>> a = 10 
>>> b = 16 
>>> a | b
26

How? In general, the bitwise operations follow some "rules":

  1. internally compare binary equivalents
  2. apply the operation
  3. return the result as the given type

Let’s apply these rules to our regular integers above.

(1) Compare binary equivalents, seen here as strings (0b denotes binary):

>>> bin(a)
'0b1010'
>>> bin(b)
'0b10000'

(2) Apply a bitwise OR operation to each column (0 when both are 0, else 1):

01010
10000
-----
11010

(3) Return the result in the given type, e.g. base 10, decimal:

>>> int(0b11010)
26

The internal binary comparison means we can apply the latter to integers in any base, e.g. hex and octal:

>>> a = 10                                   # 10, dec
>>> b = 0b10000                              # 16, bin
>>> c = 0xa                                  # 10, hex
>>> d = 0o20                                 # 16, oct

>>> a | b
26
>>> c | d
26

See Also

+The in-place bitwise OR operator cannot be applied to literals; assign objects to names.

++Special methods return the same operations as their corresponding operators.

Answered By: pylang

It’s bitwise or.
Let’s say we have 32 | 10, picture 32 and 10 in binary:

32 = 10 0000
10 = 00 1010

Now because | is the OR operation, do a bitwise-or on the two numbers

i.e 1 or 0 –> 1, 0 or 0 –> 0. Continue this down the chain:

10 0000 | 00 1010 = 10 1010.

Now change the binary into a decimal, 10 1010 = 42.

For |=, think of the known examples, x +=5. It means x = x + 5, therefore if we have x |= 5, it means x = x bitwiseor with 5.

Answered By: memeKing

In Python,|=(ior) works like union operation.
like if x=5 and x|=5 then both the value will first convert in binary value then the union operation will perform and we get the answer 5.

Answered By: aanchal.s

To give a use-case (after spending time with the other answers):

def process(item):
   return bool(item) # imagine some sort of complex processing taking place above

def any_success(data): # return True if at least one is successful
    at_least_one = False
    for item in data:
       at_least_one |= process(item)
    return at_least_one

>>> any_success([False, False, False])
False
>>> any_success([True, False, False])
True
>>> any_success([False, True, False])
True

Basically any without the short-circuiting: might be useful if you need to process every item and record at least one success etc.

See also the caveats in this answer

Answered By: scharfmn

Hopefully this also helps others to understand:

dict1 = {'a': 'dict1', 'b': 'dict1', 'c': 'dict1'}
dict2 = {'c': 'dict2', 'd': 'dict2', 'e': 'dict2'}

dict3 = dict1.copy()
dict3 = dict3 | dict2
dict4 = dict1.copy()
dict4 |= dict2
print(f'dict1:n {dict1}')
print(f'dict2:n {dict2}')
print(f'dict1 after dict1 = dict1 | dict2 (dict2 index c replaces dict1 index c, items in dict1 are discarded if present in dict2):n {dict3}')
print(f'dict1 after dict1 |= dict2 (same behaviour as dict1 = dict1 | dict2):n {dict4}')

dict5 = dict1.copy()
dict5 = dict2 | dict5
dict6 = dict2.copy()
dict6 |= dict1
print(f'dict1 after dict1 = dict2 | dict1 (dict2 index c is missing, dict1 index c was retained, items in dict2 are discarded if present in dict1):n {dict5}')
print(f'dict2 after dict2 |= dict1 (same behaviour as dict2 = dict2 | dict1):n {dict6}')


dict1:
 {'a': 'dict1', 'b': 'dict1', 'c': 'dict1'}
dict2:
 {'c': 'dict2', 'd': 'dict2', 'e': 'dict2'}
dict1 after dict1 = dict1 | dict2 (dict2 index c replaces dict1 index c, items in dict1 are discarded if present in dict2):
 {'a': 'dict1', 'b': 'dict1', 'c': 'dict2', 'd': 'dict2', 'e': 'dict2'}
dict1 after dict1 |= dict2 (same behaviour as dict1 = dict1 | dict2):
 {'a': 'dict1', 'b': 'dict1', 'c': 'dict2', 'd': 'dict2', 'e': 'dict2'}
dict1 after dict1 = dict2 | dict1 (dict2 index c is missing, dict1 index c was retained, items in dict2 are discarded if present in dict1):
 {'c': 'dict1', 'd': 'dict2', 'e': 'dict2', 'a': 'dict1', 'b': 'dict1'}
dict2 after dict2 |= dict1 (same behaviour as dict2 = dict2 | dict1):
 {'c': 'dict1', 'd': 'dict2', 'e': 'dict2', 'a': 'dict1', 'b': 'dict1'}
Answered By: NotoriousPyro

It means bitwise OR operation.

Example :

x = 5
x |= 3 #which is similar to x = x | 3
print(x)

Answer : 7

How does it works?

The binary of 5 is : 0 1 0 1
The binary of 3 is : 0 0 1 1

OR operation : (If one of both sides are 1/True then result is 1/True)

0 1 0 1  #Binary of 5
0 0 1 1  #Binary of 3
---------------------
0 1 1 1  #Binary of 7

So, the answer is 7

Answered By: XpressGeek

| is bitwise OR. So x |= y is equivalent* to x = x | y.

For sets, | takes on a related meaning: set unions. The same way you would take the intersection of 2 sets in math using OR, you can do it in python using |

*Note: The 2 expressions are not 100% equivalent. After x |= y, id(x) == id(y). After x = x | y, id(x) != id(y)

Answered By: Alec
Categories: questions Tags:
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.