On Wed, 14 Dec 2016 07:27 am, paoli...@gmail.com wrote: > The official Python tutorial at > > https://docs.python.org/3/tutorial/classes.html#private-variables > > says that "name mangling is helpful for letting subclasses override > methods without breaking intraclass method calls" and makes an interesting > example: > > class Mapping: > def __init__(self, iterable): > self.items_list = [] > self.__update(iterable) > > def update(self, iterable): > for item in iterable: > self.items_list.append(item) > > __update = update # private copy of original update() method > > class MappingSubclass(Mapping): > > def update(self, keys, values): > # provides new signature for update() > # but does not break __init__() > for item in zip(keys, values): > self.items_list.append(item) > > > It seems to me that, in this example, one could just have: > > class Mapping: > def __init__(self, iterable): > self.items_list = [] > Mapping.update(self, iterable) > > def update(self, iterable): > for item in iterable: > self.items_list.append(item) > > and avoid copying 'Mapping.update' into 'Mapping.__update'.
Perhaps. But remember that copying Mapping.update in this way is very cheap: it's only a new reference (e.g. a copy of a pointer), it doesn't have to copy the entire function object. The differences between: Mapping.update(self, iterable) and self.__update(iterable) are very subtle and (as far as I can see) only matter in some fairly hairy situations. Thanks to name mangling, the second is equivalent to: self._Mapping__update(iterable) which gives subclasses the opportunity to override it, if they dare. They probably shouldn't, because it is a private method, but it you really, really need to, you can. A more exotic difference is that the first example looks directly at the class, while the second checks for an instance attribute first, giving the instance the opportunity to shadow _Mapping__update. One last subtle difference: the second version will work even if you bind another object to Mapping: class Mapping: ... instance = Mapping() # create instance Mapping = None # rebind the name to something else d = type(instance)(iterable) # create a new instance In this (admittedly exotic) situation Raymond Hettinger's code with self.__update will continue to work perfectly, while your alternative with Mapping.update will fail. I don't know if Raymond has an objective reason for preferring one over the other, or if it is just a matter of personal taste. If you have a Twitter account, perhaps you could ask him to comment? https://twitter.com/raymondh -- Steve “Cheer up,” they said, “things could be worse.” So I cheered up, and sure enough, things got worse. -- https://mail.python.org/mailman/listinfo/python-list