如果一个对象是不可散列的,比如一个set,那么询问它是否是字典中的键是错误的:
>>> key = set()
>>> key in {}
Traceback (most recent call last):
TypeError: unhashable type: 'set'我只是想知道为什么会这样。
编辑:我知道对象需要散列,但不知道为什么它需要是一个错误,如果它不能。
发布于 2017-04-29 03:12:28
这是因为为了检查是否在字典中,Python需要做的第一件事就是尝试散列对象。
作为另一种设计决策,Python可能已经处理了这种情况;它将在dict.__contains__实现中完成,捕获TypeError并返回False。但与不处理异常相比,这为用户提供的信息更少,因此可以说用处较小。
发布于 2017-04-29 03:12:44
这是因为检查字典成员资格要求首先对对象进行散列,然后使用__eq__进行比较。
考虑下面的玩具示例:
class Key(object):
def __hash__(self):
print('calling hash')
return 1
def __eq__(self, other):
print('calling eq')
return True
dct = {1: 2}
Key() in dct
# calling hash
# calling eq在您的示例中,set()无法通过散列阶段,并且会正确地引发错误,而不是静默传递。
发布于 2017-04-29 03:14:48
将集合作为字典中的关键字是有问题的,因为集合是一个可变的数据结构。
当你将一些东西添加到集合中时会发生什么?应该继续将'a‘视为字典中的关键字,还是应该将具有a的原始值的其他集合视为关键字?
要使用类似set的结构作为键,请使用不可变的“frozenset”。您不能在实例化之后更改frozenset的值,因此python可以安全地允许它成为dict中的一个键。
https://stackoverflow.com/questions/43687330
复制相似问题