如何测试Python对象的不相等?

时间:2017-07-11 11:25:30

标签: python python-3.x unit-testing

最近,我一直在为我开发的课程编写大量的单元测试。这是我第一次采用在发布之前严格测试我的库代码的方法,我不得不同意我的 在这个过程中学到了很多东西。

我目前面临的挑战是测试两个平等和不平等的实例。

这是一个抽象库代码的简单类:

class User(object):
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def __eq__(self, other):
        if isinstance(other, self.__class__):
            return self.name == other.name and self.age == other.age

        return False

以下是我为测试相等功能而编写的单元测试:

foo = User('Kshitij', 21)
bar = User('Leo', 30)

self.assertEqual(foo, User('Kshitij', 21))
self.assertNotEqual(foo, bar)

这两个测试用例都运行良好。 但是,通过assertNotEqual方法,我正在测试__ne__()类的User。我发现这有点误导,因为我没有在我的__ne__类中实现自定义User方法。

由于这种困境,我想到用self.assertFalse(foo.__eq__(bar))self.assertFalse(foo == bar)替换非等式测试用例。

我知道所有这些方法都执行相同的任务,这个问题最初可能看起来非常主观。但是,我正在寻找一些关于测试的基本建议/原则,这可以帮助我解决类似的困境。

2 个答案:

答案 0 :(得分:1)

Python data model是这类问题的好资源:

  

默认情况下,__ne__()委托给__eq__()并反转结果,除非它是NotImplemented。比较运算符之间没有其他隐含的关系,例如,(x<yx==y)的真实性并不意味着x<=y。要从单个根操作自动生成排序操作,请参阅functools.total_ordering()

这意味着测试self.assertNotEqual(foo, bar)完全没问题,因为通过实施__eq__而不是覆盖__ne__,您隐式定义{{1} }。

但是你不需要明确地测试它(但你可以),因为它是数据模型保证之一。

然而,有一件事可能导致问题(错误),应该在单元测试中讨论:

__ne__

是一种红旗(if isinstance(other, self.__class__) isinstance组合)。

在这种特定情况下,如果处理子类,它将无法工作(因为那时self.__class__可以是子类)。

您应该对基类进行硬编码:

self.__class__

或使用duck-typing:

if isinstance(other, User):

或类似的东西。

答案 1 :(得分:0)

在进行对象比较时,默认情况下Python检查对象的内存地址(iirc,id(obj)值)

您应手动覆盖__eq__()__ne__()方法。