[issue32513] dataclasses: make it easier to use user-supplied special methods
Guido van Rossum
report at bugs.python.org
Wed Jan 24 20:33:14 EST 2018
Guido van Rossum <guido at python.org> added the comment:
Raising for order=True if one of the ordering dunders exists sounds fine.
I am confused by the corner case for hash. Your table:
"""
eq=? frozen=? __hash__
False False do not generate __hash__
False True do not generate __hash__
True False set __hash__ to None unless it already exists
True True generate __hash__ unless it already exists
and is None
"""
Then you write at the end of that message:
"""
One special case to recognize is if the class defines a __eq__. In this case, Python will assign __hash__=None before the dataclass decorator is called. The decorator cannot distinguish between these two cases (except possibly by using the order of __dict__ keys, but that seems overly fragile):
@dataclass
class A:
def __eq__(self, other): pass
@dataclass
class B:
def __eq__(self, other): pass
__hash__ = None
This is the source of the last line in the above table: for a dataclass where eq=True, frozen=True, and hash=None, if __hash__ is None it will still be overwritten. The assumption is that this is what the user wants, but it's a tricky corner case. It also occurs if setting hash=True and defining __eq__. Again, it's not expected to come up in normal usage.
"""
I think I understand what you are saying there -- the two cases are treated the same, and a __hash__ is created (assuming the decorator is really "@dataclass(eq=True, frozen=True)"), overwriting the "__hash__ = None" for class B.
However the table's last line says "generate __hash__ unless it already exists and is None". Perhaps that was a typo and you meant to write "and is *not* None"?
----------
_______________________________________
Python tracker <report at bugs.python.org>
<https://bugs.python.org/issue32513>
_______________________________________
More information about the Python-bugs-list
mailing list