On Sat, Feb 17, 2018 at 6:40 PM, Guido van Rossum <gu...@python.org> wrote:
>
>
> That's a pretty tricky proposal, and one that's been debated on and off
> for a long time in other contexts. And that flag would somehow have to be
> part of every instance's state.
>

> In general the right way to initialize an immutable/frozen object is not
> through __init__ but through __new__ -- have you tried that?
>

Constructing it throught __new__ doesn't actually work as it has no way to
alter the arguments that are passed into __init__, I think creating a
metaclass that overides __call__ is required to acheive the desired result.
Although a factory classmethod would acheive similar api.


>
> Also, a small example that demonstrates your need would do wonders to help
> us understand your use case better.
>
>

# unrelated object
class NamedObject:
    @property
    def name(self) -> str:
        return "some name"

// has may subclasses
@dataclass
class Item:
    name: str


@dataclass
class NamedObjectItem(Item):
    name: str = field(init=False)
    obj: NamedObject

    def __post_init__(self):
        self.name = self.obj.name

This works fine, until I decided them Item and therefore all subclasses
should be frozen as no instances are mutated
and if they are ever in the future then its a bug. But to do this the
following factory method needs to be added:

@classmethod
def create(cls, obj: NamedObject, *args, **kwargs):
    return cls(obj.name, obj, *args, **kwargs)

This doesn't look that bad but all fields(up to the last field used that
would have been used in __post_init__) needs to be declared in the
signature.

Thanks
Ben Lewis
_______________________________________________
Python-Dev mailing list
Python-Dev@python.org
https://mail.python.org/mailman/listinfo/python-dev
Unsubscribe: 
https://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com

Reply via email to