A class subclass of itself. Why mutual subclassing is forbidden?
我认为这个问题很复杂,但是研究猫头鹰打开了一个新的视角来生活,宇宙和一切。我要学哲学了。
我正在尝试实现一个C类,它是B的子类,反过来又是C的子类。只是为了好玩,你知道…
就在这里
1 2 3 4 5 6 7 8 9 10 11 12 13 | >>> class A(object): pass ... >>> class B(A): pass ... >>> class C(B): pass ... >>> B.__bases__ (<class '__main__.A'>,) >>> B.__bases__ = (C,) Traceback (most recent call last): File"<stdin>", line 1, in <module> TypeError: a __bases__ item causes an inheritance cycle >>> |
显然,python很聪明,禁止这样做。然而,在OWL中,可以将两个类定义为相互的子类。问题是:什么是令人难以置信的解释为什么这是允许在OWL(不是编程语言)和不允许在编程语言?
Python不允许这样做,因为没有明智的方法。关于如何处理这种情况,您可以发明任意的规则(也许有些语言也有),但是由于这样做没有实际的好处,所以Python拒绝猜测。由于许多原因,类需要具有稳定的、可预测的方法解析顺序,因此不允许使用奇怪的、不可预测的或令人惊讶的MRO。
也就是说,在python中有一个特殊的例子:
这种"分离"的一部分是因为owl描述了一个开放世界的本体论。一个本体与一个程序几乎没有关系,或者根本没有关系,除了一个程序可以操纵一个本体。
试图把猫头鹰的概念与编程语言联系起来,就像试图把钢琴家和钢琴奏鸣曲联系起来。
奏鸣曲只有在有人演奏之前才有具体的表现——理想的是钢琴家,但不一定。在演奏之前,它只是音符之间的潜在关系,表现为声音。当它被播放时,一些实际的关系将与你、听众相关。有些与听众无关。
在python中实现的MRO方案(从2.3开始)禁止循环子类化。有效的MRO保证满足"局部优先"和"单调性"。循环子类化将打破单调性。
这一问题将在题为"不良方法解决顺序"的章节中讨论。
对于语义推理者来说,如果a是b的一个子类,而b是a的一个子类,那么这些类就可以被认为是等价的。它们不是"相同的",但从推理的角度来看,如果我能解释一个人是(或不是)A类的成员,我就能解释这个人是(或不是)B类的成员。A类和B类在语义上是相等的,这就是你能用owl表达的。
我认为答案是"当你构造C类…它必须创建类B的实例。它必须创建类C的实例…等等,"这永远不会结束。在大多数语言中这是禁止的(事实上我不知道其他情况)。您只能创建一个对其他对象具有"引用"的对象,该对象最初可以为空。
我相信有人能举一个有意义的例子。不过,我想这个限制更容易,而且也不弱。
例如,假设A类包含字段A和字段B,C类包含字段B和字段C,那么C类对事物的看法是:A.A、C.B、C.C,而A类对事物的看法是:A.A、A.B、C.C。
不过,将B移到一个公共的基类中更容易理解和实现。