为什么可变实体不能成为字典键?

d33*_*tah 1 python dictionary

考虑以下Python解释器shell会话:

>>> class D(dict):
...   def __hash__(self):
...     return id(self)
... 
>>> d1 = D({'a': 'b'})
>>> d2 = D({'a1': 'b1'})
>>> t = {d1: 1, d2: 2}
>>> t[d1]
1
>>> t[d2]
2
Run Code Online (Sandbox Code Playgroud)

为什么没有dict的__hash__默认值id()?导致禁止使用可变实体作为字典键的设计决定是什么?

use*_*ica 6

为什么没有dict的__hash__默认值id()

因为这违反了基本不变量,即相等的物体具有相等的哈希值.如果dicts使用它们id作为哈希,那么你将有如下的交互:

>>> x, y = {}, {}
>>> x == y
True
>>> hash(x) == hash(y)
False
>>> x[{}] = 3
>>> x[{}]
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
KeyError: {}
Run Code Online (Sandbox Code Playgroud)

这种行为会令人困惑,不一致,也没有用处.