您好,欢迎访问一九零五行业门户网

详解Python中内置的NotImplemented类型的用法

它是什么?
>>> type(notimplemented)
notimplemented 是python在内置命名空间中的六个常数之一。其他有false、true、none、ellipsis 和 __debug__。和 ellipsis很像,notimplemented 能被重新赋值(覆盖)。对它赋值,甚至改变属性名称, 不会产生 syntaxerror。所以它不是一个真正的“真”常数。当然,我们应该永远不改变它。 但是为了完整性:
>>> none = 'hello'...syntaxerror: can't assign to keyword>>> notimplementednotimplemented>>> notimplemented = 'do not'>>> notimplemented'do not'
它有什么用?什么时候用?
notimplemented 是个特殊值,它能被二元特殊方法返回(比如__eq__() 、 __lt__() 、 __add__() 、 __rsub__() 等),表明某个类型没有像其他类型那样实现这些操作。同样,它或许会被原地处理(in place)的二元特殊方法返回(比如__imul__()、__iand__()等)。还有,它的实际值为true:
>>> bool(notimplemented)true
你也许会问自己,“但我认为当这个操作没有实现时,我应该产生个notimpementederror”。我们会看些例子,关于为什么当实现二元特殊方法时不是这么回事儿。
让我们看看notimplemented常数的用法,通过__eq__()对于两个非常基本(且没用)的类 a 和 b 的编码。[对于这个简单的例子,为了避免干扰,不会实现__ne__() ,但是总的说来,每次实现__eq__() 时, __ne__()也应该被实现,除非,有个足够充分的理由去不实现它。]
# example.py class a(object): def __init__(self, value): self.value = value def __eq__(self, other): if isinstance(other, a): print('comparing an a with an a') return other.value == self.value if isinstance(other, b): print('comparing an a with a b') return other.value == self.value print('could not compare a with the other class') return notimplemented class b(object): def __init__(self, value): self.value = value def __eq__(self, other): if isinstance(other, b): print('comparing a b with another b') return other.value == self.value print('could not compare b with the other class') return notimplemented
现在,在解释器中:
>>> from example import a, b>>> a1 = a(1)>>> b1 = b(1)
我们现在可以实验下对于 __eq__() 不同的调用,看看发生了什么。作为提醒,在python中,a == b会调用a.__eq__(b):
>>> a1 == a1comparing an a with an atrue
正如所望,a1等于a1(自己),使用类a中的__eq__()来进行这个比较的。比较b1和它自己也会产生类似结果:
>>> b1 == b1comparing a b with another btrue
现在,那要是我们比较a1和b1呢?由于在a的__eq__()会检查other是不是b的一个实例,我们想要a1.__eq__(b1)去处理这个比较并返回true:
>>> a1 == b1comparing an a with a btrue
就是这样。现在,如果我们比较b1和a1(即调用b1.__eq__(a1)),我们会想要返回notimplemented。这是因为b的__eq__()只和其他b的实例进行比较。来看看发生了什么:
>>> b1 == a1could not compare b against the other classcomparing an a with a btrue
聪明!b1.__eq__(a1)方法返回notimplemented,这样会导致调用a中的__eq__()方法。而且由于在a中的__eq__()定义了a和b之间的比较,所以就得到了正确的结果(true)。
这就是返回了notimplemented的所做的。notimplemented告诉运行时,应该让其他对象来完成某个操作。在表达b1 == a1中,b1.__eq__(a1)返回了notimplemented,这说明python试着用a1.__eq__(b1)。由于a1足够可以返回true,因此这个表达可以成功。如果a中的__eq__()也返回notimplemented,那么运行时会退化到使用内置的比较行为,即比较对象的标识符(在cpython中,是对象在内存中的地址)。
注意:如果在调用b1.__eq__(a1)时抛出notimpementederror,而不进行处理,就会中断代码的执行。而notimplemented无法抛出,仅仅是用来进一步测试是否有其他方法可供调用。
其它类似信息

推荐信息