Author Aaron.Staley
Recipients Aaron.Staley, docs@python
Date 2012-08-02.22:23:42
SpamBayes Score -1.0
Marked as misclassified Yes
Message-id <1343946223.73.0.562621858875.issue15542@psf.upfronthosting.co.za>
In-reply-to
Content
The documentation for __new__ at http://docs.python.org/reference/datamodel.html#object.__new__ is:
"""
object.__new__(cls[, ...])
Called to create a new instance of class cls. __new__() is a static method (special-cased so you need not declare it as such) that takes the class of which an instance was requested as its first argument. The remaining arguments are those passed to the object constructor expression (the call to the class). The return value of __new__() should be the new object instance (usually an instance of cls).

Typical implementations create a new instance of the class by invoking the superclass’s __new__() method using super(currentclass, cls).__new__(cls[, ...]) with appropriate arguments and then modifying the newly-created instance as necessary before returning it.

If __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.

__new__() is intended mainly to allow subclasses of immutable types (like int, str, or tuple) to customize instance creation. It is also commonly overridden in custom metaclasses in order to customize class creation.
"""


The problem is in this line: "If __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__()."

This is only true in the context of a constructor. In particular, directly calling cls.__new__(cls) will NOT call __init__.

If I define a class:
  
class C(object):
  def __new__(*args, **kwargs):
    print 'new', args, kwargs
    return object.__new__(*args,**kwargs)
  def __init__(self):
    print 'init'

C() will result in __new__ and __init__ being both executed, but C.__new__(C) will only create the instance of C; it will not call __init__!

The original documentation described in http://bugs.python.org/issue1123716 was more correct:

"__new__ must return an object... If you return an
existing object, the constructor call will still call
its __init__ method unless the object is an instance of
a different class..."

That is __init__ is only being called in the context of an external constructor call.  

Proposed phrasing:
"If __new__() is invoked during object construction (cls()) and it 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 the object constructor."
History
Date User Action Args
2012-08-02 22:23:44Aaron.Staleysetrecipients: + Aaron.Staley, docs@python
2012-08-02 22:23:43Aaron.Staleysetmessageid: <1343946223.73.0.562621858875.issue15542@psf.upfronthosting.co.za>
2012-08-02 22:23:43Aaron.Staleylinkissue15542 messages
2012-08-02 22:23:42Aaron.Staleycreate