On 06/19/2017 07:44 PM, Steven D'Aprano wrote:
On Mon, Jun 19, 2017 at 07:36:09PM -0700, Ethan Furman wrote:
On 06/19/2017 07:26 PM, Steven D'Aprano wrote:

Or maybe we decide that it's actually a feature, not a problem, for an
AttributeError inside self.attr.__get__ to look like self.attr is
missing.

It's a feature.  It's why Enum classes can have members named 'value' and
'name'.

Can you explain further? What's special about value and name?

value and name are attributes of every Enum member; to be specific, they are descriptors, and so live in the class namespace. Enum members also live in the class namespace, so how do you get both a member name value and the value descriptor to both live in the class namespace?

Easy. ;) Have the "value" and "name" descriptors check to see if they are being called on an instance, or an the class. If called on an instance they behave normally, returning the "name" or "value" data; but if called on the class the descriptor raises AttributeError, which causes Python to try the Enum class' __getattr__ method, which can find the member and return it... or raise AttributeError again if there is no "name" or "value" member.

Here's the docstring from the types.DynamicClassAttribute in question:

class DynamicClassAttribute:
    """Route attribute access on a class to __getattr__.

    This is a descriptor, used to define attributes that act differently when
    accessed through an instance and through a class.  Instance access remains
    normal, but access to an attribute through a class will be routed to the
    class's __getattr__ method; this is done by raising AttributeError.

    This allows one to have properties active on an instance, and have virtual
    attributes on the class with the same name (see Enum for an example).
    """

--
~Ethan~
_______________________________________________
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/

Reply via email to