[Tutor] use of __new__

Kent Johnson kent37 at tds.net
Fri Jun 12 16:30:44 CEST 2009


On Fri, Jun 12, 2009 at 10:03 AM, spir<denis.spir at free.fr> wrote:
> Don't you have a comment in the 'if' case, too? Namely that __init__ is not invoked explicitely, while the docs clearly state:
>
> << f __new__() returns an instance of cls, then the new instance’s __init__() method will be invoked like __init__(self[, ...]), where self is the new instance and the remaining arguments are the same as were passed to __new__().
>
> If __new__() does not return an instance of cls, then the new instance’s __init__() method will not be invoked.>>

It's hard to talk about this clearly because there are *two*
invocations of __new__(). Using your original names of Normal and
Special,

when you call Normal(), that invokes Normal.__new__(). If you then
call Special(), that invokes Special.__new__(). This invocation
returns an instance of Special, so Special.__init__() is also called.
The invocation of Normal.__new__() will not invoke Special.__init__().

This all happens in type.__call__(), which is the special method that
is invoked by Normal(). (Normal is an instance of type, so Normal()
invokes type.__call__().) You can look at the source, it is in
typeobject.c in the type_call method. Simplified, it looks something
like this:

def __call__(cls, *args, **kwds): # this is a metaclass method so
'self' is the class
  obj = cls.__new__(*args, **kwds)
  if obj is not None and isinstance(obj, cls):
    obj.__init__(*args, **kwds)
  return obj

Kent


More information about the Tutor mailing list