Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why do Python classes inherit 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... 
like image 476
tjvr Avatar asked Oct 25 '10 14:10

tjvr


People also ask

Why does Python class inherit from object?

They decided that they would use a word "object", lowercased, to be the "class" that you inherit from to make a class. It is confusing, but a class inherits from the class named "object" to make a class but it's not an object really its a class, but don't forget to inherit from object.

What is the purpose of inheritance Python?

Inheritance allows us to define a class that inherits all the methods and properties from another class. Parent class is the class being inherited from, also called base class. Child class is the class that inherits from another class, also called derived class.

Why are classes objects in Python?

A class is a user-defined blueprint or prototype from which objects are created. Classes provide a means of bundling data and functionality together. Creating a new class creates a new type of object, allowing new instances of that type to be made.


1 Answers

Is there any reason for a class declaration to inherit from object?

In Python 3, apart from compatibility between Python 2 and 3, no reason. In Python 2, many reasons.


Python 2.x story:

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:

  1. "classic" style classes: they don't have object as a base class:

    >>> class ClassicSpam:      # no base class ...     pass >>> ClassicSpam.__bases__ () 
  2. "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:

    1. classmethod: A method that receives the class as an implicit argument instead of the instance.
    2. staticmethod: A method that does not receive the implicit argument self as a first argument.
    3. properties with property: Create functions for managing the getting, setting and deleting of an attribute.
    4. __slots__: Saves memory consumptions of a class and also results in faster attribute access. Of course, it does impose limitations.
  • The __new__ static method: lets you customize how new class instances are created.

  • Method resolution order (MRO): in what order the base classes of a class will be searched when trying to resolve which method to call.

  • Related to MRO, super calls. Also see, super() considered super.

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.x story:

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 

and to this:

class Spam():     pass 

All have object in their __bases__.

>>> [object in cls.__bases__ for cls in {Spam, NewSpam, ClassicSpam}] [True, True, True] 

So, what should you do?

In Python 2: always inherit from object explicitly. Get the perks.

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.

like image 118
Dimitris Fasarakis Hilliard Avatar answered Dec 11 '22 04:12

Dimitris Fasarakis Hilliard