inconsistency with += between different types ?

Huaiyu Zhu huaiyu at gauss.almadan.ibm.com
Mon Aug 5 18:54:07 EDT 2002


Jonathan Hogg <jonathan at onegoodidea.com> wrote:
>On 5/8/2002 20:50, in article aimku1$22ce$1 at nntp6.u.washington.edu, "Donn
>Cave" <donn at u.washington.edu> wrote:
>
>> The way I see it, he's right on target with ``whether and how __iadd__
>> is implemented''  It's true that you can't expect to see immutable
>> objects modified, a contradiction in terms, but you certainly can
>> implement a mutable object that reassigns to the left hand side.
>> So mutability isn't the real issue (as usual.)
>
>I'm not sure I'm following what you mean. Do you mean you think that:
>
>>>> x += y
>
>should simply be a shortcut for:
>
>>>> x = x + y
>
>with mutable objects?
>
>This doesn't make sense to me. 'iadd' or, "in-place add", is fairly clear in
>meaning. It means the LHS should add the RHS to *itself*. In the case of
>immutable objects this simply can't occur and so the result is simply a
>re-assignment. With mutable objects, they should certainly modify
>themselves.

That's what it should be.  Yet it is possible for whoever writes __iadd__ to
define it the other way.  I think this is exactly Donn's point: that += was
designed in such a way that both semantics are allowed under the same
notation.

Consider this table:

                in place         assignment
            +---------------+----------------+
mutable     |       A       |        B       |
            +---------------+----------------+
immutable   |       C       |        D       |
            +---------------+----------------+

The main reason for adding += was A.  Yet it was deemed necessary to also
work for immutable types.  Of course C is impossible.  Since D was also
desired by many people, it was implemented to allow both A and D.  However,
that leaves B to be a possibility as well.

So for mutable objects, the only way to know whether it takes A or B
semantics is to check out the implementation of __iadd__ (or lack of it).

This issue was debated here at the time this feature was about to go in.
Several people warned of the confusion that would follow.  Many suggestions
were made (such as using += and +! or +: to differentiate these two
semantics).  In the end none of that discussion had much impact.
Consequently we are seeing frequent questions on this issue.  Now that it's
in, to separate them out retroactively would be a similar undertaking as
separating / and //, IMHO.

Huaiyu




More information about the Python-list mailing list