为什么 Python 类会继承对象?
问题描述
类声明是否有任何理由从 object
继承?
Is there any reason for a class declaration to inherit from object
?
我刚刚找到了一些执行此操作的代码,但我找不到很好的理由.
I just found some code that does this and I can't find a good reason why.
class MyClass(object):
# class code follows...
解决方案
类声明是否有任何理由从
object
继承?
在 Python 3 中,除了 Python 2 和 3 的兼容性之外,没有理由.在 Python 2 中,原因很多.
In Python 3, apart from compatibility between Python 2 and 3, no reason. In Python 2, many reasons.
在 Python 2.x(从 2.2 开始)中,有两种样式的类,具体取决于是否存在 object
作为基类:
In Python 2.x (from 2.2 onwards) there's two styles of classes depending on the presence or absence of object
as a base-class:
经典"风格类:它们没有
object
作为基类:
"classic" style classes: they don't have
object
as a base class:
>>> class ClassicSpam: # no base class
... pass
>>> ClassicSpam.__bases__
()
新"样式类:它们直接或间接拥有(例如从内置类型),object
作为基类:
"new" style classes: they have, directly or indirectly (e.g inherit from a built-in type), object
as a base class:
>>> class NewSpam(object): # directly inherit from object
... pass
>>> NewSpam.__bases__
(<type 'object'>,)
>>> class IntSpam(int): # indirectly inherit from object...
... pass
>>> IntSpam.__bases__
(<type 'int'>,)
>>> IntSpam.__bases__[0].__bases__ # ... because int inherits from object
(<type 'object'>,)
毫无疑问,在编写课程时,您会总是想要选择新式课程.这样做的好处很多,列举其中一些:
Without a doubt, when writing a class you'll always want to go for new-style classes. The perks of doing so are numerous, to list some of them:
对描述符的支持.具体来说,使用描述符可以实现以下构造:
Support for descriptors. Specifically, the following constructs are made possible with descriptors:
classmethod
:一种方法接收类作为隐式参数而不是实例.staticmethod
:一种方法不接收隐式参数self
作为第一个参数.- 具有
property
的属性:创建用于管理属性的获取、设置和删除的功能. __slots__
:节省内存消耗一个类,也导致更快的属性访问.当然,它确实施加限制.
classmethod
: A method that receives the class as an implicit argument instead of the instance.staticmethod
: A method that does not receive the implicit argumentself
as a first argument.- properties with
property
: Create functions for managing the getting, setting and deleting of an attribute. __slots__
: Saves memory consumptions of a class and also results in faster attribute access. Of course, it does impose limitations.
__new__
静态方法:让您自定义如何创建新的类实例.
The __new__
static method: lets you customize how new class instances are created.
方法解析顺序(MRO):按什么顺序尝试解析调用哪个方法时,将搜索类的基类.
Method resolution order (MRO): in what order the base classes of a class will be searched when trying to resolve which method to call.
与 MRO 相关,super
调用.另请参阅,super()
被认为是超级的.
Related to MRO, super
calls. Also see, super()
considered super.
如果你不是从 object
继承的,忘记这些.可以在 这里.
If you don't inherit from object
, forget these. A more exhaustive description of the previous bullet points along with other perks of "new" style classes can be found here.
新型类的缺点之一是类本身需要更多内存.但是,除非您要创建许多类对象,否则我怀疑这将是一个问题,并且它是在积极海洋中的消极沉没.
One of the downsides of new-style classes is that the class itself is more memory demanding. Unless you're creating many class objects, though, I doubt this would be an issue and it's a negative sinking in a sea of positives.
在 Python 3 中,事情被简化了.只有新样式的类存在(简单地称为类),所以添加 object
的唯一区别是要求您再输入 8 个字符.这个:
In Python 3, things are simplified. Only new-style classes exist (referred to plainly as classes) so, the only difference in adding object
is requiring you to type in 8 more characters. This:
class ClassicSpam:
pass
完全等同于(除了他们的名字:-):
is completely equivalent (apart from their name :-) to this:
class NewSpam(object):
pass
对此:
class Spam():
pass
所有的 __bases__
中都有 object
.
>>> [object in cls.__bases__ for cls in {Spam, NewSpam, ClassicSpam}]
[True, True, True]
<小时>
那么,你应该怎么做?
在 Python 2 中: 总是从 object
显式继承.获得福利.
So, what should you do?
In Python 2: always inherit from object
explicitly. Get the perks.
在 Python 3 中: 从 object
继承,如果您编写的代码试图与 Python 无关,也就是说,它需要在 Python 2 和 Python 中都可以工作3. 否则不要,真的没什么区别,因为Python会在幕后为你插入.
In Python 3: inherit from object
if you are writing code that tries to be Python agnostic, that is, it needs to work both in Python 2 and in Python 3. Otherwise don't, it really makes no difference since Python inserts it for you behind the scenes.
相关文章