On Dec 6, 3:02 pm, samwyse <[EMAIL PROTECTED]> wrote: > On Dec 6, 1:12 pm, "Diez B. Roggisch" <[EMAIL PROTECTED]> wrote: > > > > > samwyse schrieb: > > > > For whatever reason, I need an inproved integer. Sounds easy, let's > > > just subclass int: > > > >>>> class test(int): > > > pass > > > > Now let's test it: > > > >>>> zed=test(0) > > >>>> zed.__class__ > > > <class '__main__.test'> > > >>>> zed > > > 0 > > > > So far, so good. Now let's try incrementing: > > > >>>> zed+=1 > > >>>> zed > > > 1 > > >>>> zed.__class__ > > > <type 'int'> > > > > WTF??! > > > Is this a bug or is it the inevitable result of optimizing for the > > > case where all integers are indistinguishable? > > > There has been a lengthe thread over the semantics of __iadd__ a few > > weeks ago. It _can_ modify the object in question in-place (something > > not possible for ints anyway), but it will ALWAYS return a reference > > which will be set to the left-hand-side. > > Thanks! I'd missed that thread, googling found it but it didn't look > noteworthy at first glance. I've not yet read the entire thread, but > I did see a reference to PEP 203. > > ) So, given the expression: > ) > ) x += y > ) > ) The object `x' is loaded, then `y' is added to it, and the > ) resulting object is stored back in the original place. > > That agrees with what I'm seeing, all right. The problem is, the > resulting object has a different type, which seems to violate the > spirit of a later paragraph: > > ) Writing the above expression as > ) > ) <x> <operator>= <y> > ) > ) is both more readable and less error prone, because it is > ) instantly obvious to the reader that it is <x> that is being > ) changed, and not <x> that is being replaced by something almost, > ) but not quite, entirely unlike <x>. > > And that's my complaint. The value in <zed> is being replaced by > something almost, but not quite, identical to the original value. > Python's internal implementation of __iadd__ for <int> isn't returning > <self>, it's returning a new value belonging to the super-class. My > whole point is overloading <int> was that I'd hoped to avoid having to > write a bunch of methods to perform in-place modifications. Looks > like I stuck, however.
I've wondered about this myself. Seems to me, to prevent clobbering subclasses, __iadd__ (and all of the integer and float and whatever) methods that return new instances, should work like this (obviously I mean in the C backend, this is just to show the behavior): def __iadd__(self, other): return self.__class__(self + other) Regards, Jordan -- http://mail.python.org/mailman/listinfo/python-list