[Python-Dev] Return type of alternative constructors

Guido van Rossum guido at python.org
Tue May 10 14:02:13 EDT 2016


On Tue, May 10, 2016 at 6:21 AM, Nick Coghlan <ncoghlan at gmail.com> wrote:

> On 10 May 2016 at 02:30, Guido van Rossum <guido at python.org> wrote:
> > On Sun, May 8, 2016 at 7:52 PM, Nick Coghlan <ncoghlan at gmail.com> wrote:
> >> P.S. It occurs to me that a sufficiently sophisticated typechecker
> >> might be able to look at all of the calls to "cls(*args, **kwds)" in
> >> class methods and "type(self)(*args, **kwds)" in instance methods, and
> >> use those to define a set of type constraints for the expected
> >> constructor signatures in subclassses, even if the current code base
> >> never actually invokes those code paths.
> >
> > Could you restate that as a concrete code example? (Examples of the
> problems
> > with "construction features" would also be helpful, probably -- abstract
> > descriptions of problems often lead me astray.)
>
> Rectangle/Square is a classic example of the constructor signature
> changing, so I'll try to use that to illustrate the point with a
> "displaced_copy" alternate constructor:
>
>     class Rectangle:
>         def __init__(self, top_left_point, width, height):
>             self.top_left_point = top_left_point
>             self.width = width
>             self.height = height
>
>         @classmethod
>         def displaced_copy(cls, other_rectangle, offset):
>             """Create a new instance from an existing one"""
>             return cls(other.top_left_point + offset, other.width,
> other.height)
>

(But why is it a class method? I guess the example could also use an
instance method and it would still have the same properties relevant for
this discussion.)


>     class Square:
>         def __init__(self, top_left_point, side_length):
>             super().__init__(top_left_point, side_length, side_length)
>
> At this point, a typechecker *could* have enough info to know that
> "Square.displaced_copy(some_rectangle, offset)" is necessarily going
> to fail, even if nothing in the application actually *calls*
> Square.displaced_copy.
>

The question remains of course whether the type checker should flag Square
to be an invalid subclass or merely as not implementing displaced_copy().

Anyway, at this point I believe we're just violently agreeing, so no need
for another response. Though Serhiy may be unhappy with the lack of
guidance he's received...

-- 
--Guido van Rossum (python.org/~guido)
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/python-dev/attachments/20160510/0c27b9bd/attachment.html>


More information about the Python-Dev mailing list