Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

semantics of the |= operator

0 views
Skip to first unread message

akva

unread,
Aug 21, 2008, 11:37:14 AM8/21/08
to
Hi All,

what's the exact semantics of the |= operator in python?
It seems that a |= d is not always equivalent to a = a | d

For example let's consider the following code:

def foo(s):
s = s | set([10])

def bar(s):
s |= set([10])

s = set([1,2])

foo(s)
print s # prints set([1, 2])

bar(s)
print s # prints set([1, 2, 10])

So it appears that inside bar function the |= operator modifies the
value of s in place rather than creates a new value.
I'm using Python 2.5

Thanks everybody,
Vitali

Diez B. Roggisch

unread,
Aug 21, 2008, 11:40:41 AM8/21/08
to
akva wrote:

Yes. That's the exact purpose of the in-place operators when they deal with
mutable objects. What else did you expect?

Now of course this behaves different:

def foo(x):
x += 1

y = 100
foo(y)
print y

will result in y still being 100, as the value 101 that is bound to x inside
foo is *not* re-bound to the name y in the outer scope. This is because
numbers (and strings and tuples) are immutables, and thus the operation
won't modify the 100 in place to become 101, instead return a new object.

Diez

Terry Reedy

unread,
Aug 21, 2008, 5:16:40 PM8/21/08
to pytho...@python.org

akva wrote:
> Hi All,
>
> what's the exact semantics of the |= operator in python?
> It seems that a |= d is not always equivalent to a = a | d

The manual explicitly specifies that mutable objects may implement the
operation part of operation-assignments by updating in place -- so that
the object assigned is a mutated version of the original rather than a
new object.

The value equivalency only applies in the namespace in which the
statement appears.

> For example let's consider the following code:
>
> def foo(s):
> s = s | set([10])
>
> def bar(s):
> s |= set([10])
>
> s = set([1,2])
>
> foo(s)
> print s # prints set([1, 2])

Put the print inside foo and you will get set([1,2,10]), as with bar.

> bar(s)
> print s # prints set([1, 2, 10])
>
> So it appears that inside bar function the |= operator modifies the
> value of s in place rather than creates a new value.

This has nothing to do with being inside a function.

tjr

akva

unread,
Aug 22, 2008, 3:35:31 AM8/22/08
to
thanks all,

>Yes. That's the exact purpose of the in-place operators when they deal with
>mutable objects. What else did you expect?

well, frankly I expected a |= b to mean exactly the same as a = a | b
regardless of the object type.

> The manual explicitly specifies that mutable objects may implement the
> operation part of operation-assignments by updating in place  -- so that
> the object assigned is a mutated version of the original rather than a
> new object.

could you please refer me a link where this is specified? I couldn't
find it
in python documentation

> This has nothing to do with being inside a function.

yes, I know. maybe my example is a bit too verbose. could avoid using
functions.
But you got my main point. I found it somewhat counter-intuitive that
operation-assignments
can modify value in place.

Regards,
Vitali

Fredrik Lundh

unread,
Aug 22, 2008, 3:56:35 AM8/22/08
to pytho...@python.org
akva wrote:

> could you please refer me a link where this is specified? I couldn't
> find it in python documentation

http://docs.python.org/ref/augassign.html

"An augmented assignment expression like x += 1 can be rewritten as x =
x + 1 to achieve a similar, but not exactly equal effect. In the
augmented version, x is only evaluated once. Also, when possible, the
actual operation is performed in-place, meaning that rather than
creating a new object and assigning that to the target, the old object
is modified instead."

</F>

Peter Pearson

unread,
Aug 22, 2008, 1:40:32 PM8/22/08
to
On Fri, 22 Aug 2008 00:35:31 -0700 (PDT), akva <kir...@gmail.com> wrote:
>
> well, frankly I expected a |= b to mean exactly the same as a = a | b
> regardless of the object type.

So did I. I'm glad your post called this to my attention; I
recently told my kid exactly that wrong thing.


--
To email me, substitute nowhere->spamcop, invalid->net.

akva

unread,
Aug 24, 2008, 4:24:09 PM8/24/08
to
thanks everybody.
0 new messages