gpt4 book ai didi

python - 如何判断一个对象/实例是否可哈希

转载 作者:太空宇宙 更新时间:2023-11-04 01:58:14 24 4
gpt4 key购买 nike

我最近发现了一个有趣的观察结果,即有些因素会影响类的对象/实例的可哈希性。我想知道如何以及为什么?

例如,我有一个名为ListNode的链表类:

class ListNode:
def __init__(self, x):
self.val = x
self.next = None

def __repr__(self):
if self.next:
return "{}->{}".format(self.val, repr(self.next))
else:
return "{}".format(self.val)

# def __eq__(self, other):
# if not self and not other:
# return True
# elif not self or not other:
# return False
# else:
# return self.val == other.val and self.next == other.next

# def __eq__(self, other):
# return str(self) == str(other)

请注意,我阻止了 __eq__ 方法。现在,如果我创建一个实例:

A = ListNode(1)
B = ListNode(2)
C = ListNode(3)
A.next = B
B.next = C
print(hash(A))

然后它是可哈希的,但是,我每次运行它时都会得到不同的输出数字。

现在,如果我取消阻止 __eq__ 方法,突然间它就不再是可哈希的了。为什么?

看来hash方法会用到__eq__。在启用 __eq__ 后,它如何知道它不可哈希?

附加:如果我编写 __eq__ 方法来比较两个链表的 str 版本(第二个 __eq__ 方法),我认为这可以解决问题,因为通过将链表转换为 string,它变成了可哈希数据,但我仍然收到 unhashable 错误消息

谢谢!

According to @juanpa.arrivillaga's comment:

__eq__ 将删除默认的 __hash__ 方法,使其不可散列。所以我添加了我自己的__hash__ 方法:

def __hash__(self):
return hash(id(self))

这解决了问题并使 ListNode__eq__ 启用的情况下再次可哈希。

最佳答案

If a class does not define an __eq__() method it should not define a __hash__() operation either; if it defines __eq__() but not __hash__(), its instances will not be usable as items in hashable collections.

(...)

A class that overrides __eq__() and does not define __hash__() will have its __hash__() implicitly set to None. When the __hash__() method of a class is None, instances of the class will raise an appropriate TypeError when a program attempts to retrieve their hash value, and will also be correctly identified as unhashable when checking isinstance(obj, collections.abc.Hashable). 1

__eq__() 方法的引入因此将 __hash__() 设置为 None。您可以添加自定义哈希,以允许上述构造:

def __hash__(self):
return self.val

您可以在此处找到更多信息:https://docs.python.org/3/reference/datamodel.html#object.hash

关于python - 如何判断一个对象/实例是否可哈希,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56298727/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com