Python新样式的类和子类函数

2024-09-26 17:52:38 发布

您现在位置:Python中文网/ 问答频道 /正文

有人能解释一下为什么这样做吗(在Python2.5中):

class Foo(object):
    pass

class Bar(Foo):
    pass

print(Foo.__subclasses__())

但这并不是:

class Foo():
    pass

class Bar(Foo):
    pass

print(Foo.__subclasses__())

后者返回“AttributeError:class Foo没有属性__subclasses__”,但我不确定原因。我知道这与旧样式类和新样式类有关,但我不清楚为什么这会使此功能不可用。

澄清:我想了解为什么__subclasses__()在旧样式中不可用,我得到的是该方法对于旧样式类不存在,但我不知道是什么关于新样式使这些新函数成为可能。


Tags: 方法函数功能属性objectfoobar原因
2条回答

加上上面的答案。

Python 3.0有一个单独的类实现。子类化是Python3.0的一个特性,而不是Python2.0。

所以如果你安装了python 3.x并且

class Foo():
    pass

class Bar(Foo):
    pass

print(Foo.__subclasses__())

它不会给出任何属性错误。

现在,通过在每个类定义中继承“object”基类,将相同的功能扩展到Python 2.0类。

因此,如果在Python 2.x中这样做:

class Foo(object):
    pass

class Bar(Foo):
    pass

print(Foo.__subclasses__())

由于您正在继承新类Foo中的object基类,因此继承了3.x样式的类,并且不会出现属性错误。

但是在Python 2.x中

class Foo():
    pass

class Bar(Foo):
    pass

print(Foo.__subclasses__())

这意味着,新样式类没有被继承,并且由于子类是新样式类的一部分,它将抛出属性错误。

所以请记住,如果要将任何Python 3.x类功能扩展到Python 2.x,您需要在类定义中继承object类。

希望这有帮助。

class Foo(object):
    pass

上面的类是一个“新样式”类,因为它继承自对象类。新样式类提供了许多“旧样式”类没有的额外框架。新样式类的一个特殊属性是能够使用\uuu subclasses\uuu方法确定类的子类。

有关于新样式类的somegooddiscussion和用于完全undocumented{u子类的方法。(Here是蒂姆·彼得斯的非正式解释。)

“每个新样式的类都保留对其直接子类的弱引用列表。此方法返回所有仍然存在的引用的列表。”

因此,要回答您的问题,无法使用\u子类功能,因为在第二个示例中:

class Foo():
    pass

旧样式类Foo不继承自对象(因此它不是一个新样式类),并且for不继承\u子类方法。

注意,如果您不理解为什么一个旧样式的类没有\u子类方法,那么您总是可以启动一个python解释器并使用dir进行一些检查

>>> class Foo(object):
...     pass
...
>>> dir(Foo.__class__)
['__abstractmethods__', '__base__', '__bases__', '__basicsize__', '__call__', '__class__', '__delattr__', '__dict__', '__dictoffset__', '__doc__', '__
eq__', '__flags__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__instancecheck__', '__itemsize__', '__le__', '__lt
__', '__module__', '__mro__', '__name__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__s
ubclasscheck__', '__subclasses__', '__subclasshook__', '__weakrefoffset__', 'mro']
>>> class Bar():
...     pass
...
>>> dir(Bar.__class__)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: class Bar has no attribute '__class__'
>>> dir(Bar)
['__doc__', '__module__']
>>> dir(Foo)
['__class__', '__delattr__', '__dict__', '__doc__', '__format__', '__getattribute__', '__hash__', '__init__', '__module__', '__new__', '__reduce__', '
__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__']

相关问题 更多 >

    热门问题