Inheritance error in python 2.3.4???

Steven Bethard steven.bethard at gmail.com
Mon Feb 14 18:35:03 EST 2005


friedmud at gmail.com wrote:
> class baseClass(object):
>         __Something = "Dumb!"
> 
>         def getSomething( self ):
>                 return self.__Something
> 
> class subClass(baseClass):
>         def setSomething( self , aSomething ):
>                 self.__Something = aSomething
> 
> 
> anObject = subClass()
> anObject.setSomething("Cool!")
> print anObject.getSomething()

Your mistake is using '__' names when they aren't necessary.  '__' names 
are mangled with the class name:

py> class B(object):
...     __x = False
...     def __init__(self):
...         self.__x = 1
...     def getx(self):
...         return self.__x
...
py> class C(object):
...     def setx(self, x):
...         self.__x = x
...
py> vars(B())
{'_B__x': 1}
py> vars(C())
{}

Note that C instances don't get __x variables because of the mangling.

> Someone please show me the pythonish way to do this!

A number of suggestions:

(1) Generally, you don't need getters and setters.  If you think you do, 
you probably want property instead.

(2) Don't use __ names.  They're a hack that doesn't really make things 
private, and doesn't even avoid name collisions all the time.  There are 
probably a few cases where they're useful, but this is not one of them. 
  If you don't want attributes to show up in automatically generated 
documentation, simply prefix them with a single underscore.

(3) Don't use class-level attributes as defaults for instance-level 
attributes.  If it's part of the instance, set it on the instance.  If 
it's part of the class, set it on the class.  Hiding a class-level 
attribute with an instance-level attribute will most likely lead to 
confusion unless you *really* know what you're doing in Python.

Something like this would probably be best:

py> class BaseClass(object):
...     def __init__(self, something='Dumb!'):
...         self._something = something
...     def _getsomething(self):
...         return self._something
...     something = property(_getsomething)
...
py> class SubClass(BaseClass):
...     def _setsomething(self, something):
...         self._something = something
...     something = property(BaseClass._getsomething, _setsomething)
...
py> b = BaseClass()
py> b.something
'Dumb!'
py> b.something = 1
Traceback (most recent call last):
   File "<interactive input>", line 1, in ?
AttributeError: can't set attribute
py> s = SubClass()
py> s.something
'Dumb!'
py> s.something = 'Cool!'
py> s.something
'Cool!'

STeVe



More information about the Python-list mailing list