pondering about the essence of types in python

Steve Holden steve at holdenweb.com
Sat Mar 25 17:09:30 EST 2006


gangesmaster wrote:
> let's start with a question:
> 
> ==========
> 
>>>>class z(object):
> 
> ...     def __init__(self):
> ...             self.blah=5
> ...
> 
>>>>class x(object):
> 
> ...     def __init__(self):
> ...             z.__init__(self)
> ...
> 
>>>>y=x()
> 
> Traceback (most recent call last):
>   File "<stdin>", line 1, in ?
>   File "<stdin>", line 3, in __init__
> TypeError: unbound method __init__() must be called with z instance as
> first argument (got x instance instead)
> ==========
> 
> and the question is -- WHY?
> 
> what is a type? generally speaking, if everything were an object, the
> type only defines the MRO (method resolution order) for that object.
> x.y first looks at the instance, then the class, then the parent
> classes, etc. (this was changed a little in python2.3 to something more
> complicated, but it's basically the same).
> 
> you can see the mro like this:
> ==========
> 
>>>>class x(object): pass
>>>>class y(x): pass
>>>>class z(y): pass
>>>>a=z()
>>>>print a.__class__.mro()
> 
> [<class '__main__.z'>, <class '__main__.y'>, <class '__main__.x'>,
> <type 'object'>]
> ==========
> 
> after all, if we stay out of builtin types, all python objects are
> dicts, which support chian-lookup according to the mro. and a method is
> just a function that takes the instance as a first argument. so why is
> all this type hassle necessary?
> 
> if we've taken it that far already, then let's really go over the edge.
> I WANT TO DERIVE FROM INSTANCES. not only types.
> 
> why? i'm the developer of rpyc (http://rpyc.sf.net), and i got a
> request from someone to add support for deriving from remote types. the
> concrete example he gave was quite silly, but after i thought about it
> a little, i said why not try?
> 
> a little intro about rpyc: it gives you proxies (instances) to remote
> objects, which can be instances, functions, or classes. and that user
> wanted to do something like this:
> 
> class my_frame(conn.modules.wx.Frame):
>     ...
> 
> so the client was actually creates the graphics on the server. not very
> usable, but why not?  all it means is, when he does "my_frame.xyz",
> python should add the remote type to the mro chain. not too bizar.
> 
> but __mro__ is a readonly attribute, and deriving from instances is
> impossible (conn.modules.wx.Frame is a PROXY to the class)...
> 
> and again -- WHY? these all look like INTENTIONAL limitations. someone
> went around and added type checks (which are NOT pythonic) into the
> cPython implementation. argh. why do that?
> 
> so i thought -- let's be nasty. i created a function that creates a
> class that wraps an instance. very ugly. small children and peope with
> heart problems should close their eyes.
> 
> ============
> def derive_from(obj):
>     class cls(object):
>         def __getattr(self, name):
>             return getattr(obj, name)
>     return cls
> 
> class my_frame(derive_from(conn.modules.wx.Frame)):
>     ....
> ============
> 
> the actual implementation is quite more complex, but that shows the
> concept.
> so now i'm experimenting with that little shit. but then i came to the
> problem that methods check the type of the first argument... ARGH. dont
> check types. DONT. the whole point of duck-typing is you DONT CHECK THE
> TYPES. you just work with objects, and instead of TypeError you'd get
> AttribiuteError, which is much better.  AAARRRRRRGGGHH.
> 
> python is EVIL at the low level. the high-level is just fine, but when
> you try to go under the hood... you better go with an exorcist.
> 
Take a look at languages like Self. Self was actually the first 
prototype-based OO language. You could consider Javascript to be a 
prototype-based language as well.

regards
  Steve
-- 
Steve Holden       +44 150 684 7255  +1 800 494 3119
Holden Web LLC/Ltd                 www.holdenweb.com
Love me, love my blog         holdenweb.blogspot.com




More information about the Python-list mailing list