列表和集合的成员资格测试有何不同?
我无法弄清楚为什么第一个断言没问题,而第二个断言却引发错误。
subject_list = [Subject("A"), Subject("B"), Subject("C")]
subject_set = set()
subject_set.add(Subject("A"))
subject_set.add(Subject("B"))
subject_set.add(Subject("C"))
self.assertIn(Subject("A"), subject_list)
self.assertIn(Subject("A"), subject_set)
错误如下:
Traceback (most recent call last):
File "C:\Users\...\testSubject.py", line 34, in testIn
self.assertIn(Subject("A"), subject_set)
AssertionError: <Subject: A> not found in set([<Subject: B>, <Subject: C>, <Subject: A>])
Subject 类中的相等性测试只是 self.name == other.name
,而在另一个 UnitTest 中,我验证 Subject("A") == subject (“A”)
。我真的不明白为什么该主题在列表中而不是在集合中。理想情况下,我希望主题同时存在于两者中。
I'm having trouble with figuring out why the first of these assertions is OK and the second raises an error.
subject_list = [Subject("A"), Subject("B"), Subject("C")]
subject_set = set()
subject_set.add(Subject("A"))
subject_set.add(Subject("B"))
subject_set.add(Subject("C"))
self.assertIn(Subject("A"), subject_list)
self.assertIn(Subject("A"), subject_set)
Here is the error:
Traceback (most recent call last):
File "C:\Users\...\testSubject.py", line 34, in testIn
self.assertIn(Subject("A"), subject_set)
AssertionError: <Subject: A> not found in set([<Subject: B>, <Subject: C>, <Subject: A>])
The test for equality in the Subject class is simply self.name == other.name
, and in another UnitTest I verify that Subject("A") == Subject("A")
. I really can't figure out why the subject is in the list and not in the set. Ideally I'd like the subject to be in both.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
该表达式
将使用
Subject.__eq__()
方法将Subject("A")
与subject_list
中的每个条目进行比较。如果不覆盖此方法,则默认情况下始终返回False
,除非两个操作数是同一对象。如果Subject
缺少__eq__()
方法,上面的表达式将始终返回False
,因为Subject("A")
> 是一个新实例,不能已在列表中。相反的表达式
将首先使用
Subject.__hash__()
来查找正确的存储桶,然后才使用Subject.__eq__()
。如果您没有以与Subject.__eq__()
兼容的方式定义Subject.__hash__()
,则此操作将会失败。The expression
will compare
Subject("A")
to each entry insubject_list
using theSubject.__eq__()
method. If this method is not overwritten, it defaults to always returnFalse
unless the two operands are the same object. The above expression would always returnFalse
ifSubject
lacked a__eq__()
method, sinceSubject("A")
is a new instance which cannot already be in the list.The expression
on the contrary will use
Subject.__hash__()
first to find the right bucket, and useSubject.__eq__()
only after this. If you did not defineSubject.__hash__()
in a way compatible withSubject.__eq__()
, this will fail.集合中的成员资格还取决于对象的哈希,因此您必须在类上适当地实现 __hash__() 方法。
Membership in a set also depends on the object's hash, and as such you must implement the
__hash__()
method on the class appropriately.要么您的
Subject
类中没有__hash__()
方法,要么它是不可靠的。试试这个:文档位于此处。
Either you don't have a
__hash__()
method in yourSubject
class, or it is dodgy. Try this:The docs are here.
要在集合中使用它们,您必须确保
Subject
可以正确散列。如果您自己没有定义__hash__
,它只会采用id
,并且对于不同的实例来说这是不同的。__hash__
的定义应使相同的对象具有相同的哈希值。To use these in a set, you have to make sure
Subject
is properly hashable. If you do not define__hash__
yourself, it will simply take theid
, and that is different for different instances.__hash__
should be defined such that equal objects have equal hashes.