I am not an expert on this but AFAIK the __init__
method is a built-in method of every class or metaclass, that is called exactly in the class instantiation.
Why or what for would you use the __init__
method?
Well, you can use it for many things, but the main purpose is to pass arguments into the class instance when it is instantiated. Actually when you do class(*args, **kwargs)
these get passed along to __init__
, where you might either make use of them or not.
For example:
class Vehicle:
name = 'vehicle'
price = None
canMove = False
position = 0
def __init__(self, price, name=None, canMove=False):
self.name = name if name else self.name
self.price = price
def move(self, distance):
if self.canMove:
self.position += distance
return 'The vehicle moved {0} meters'.format(distance)
return 'The vehicle cannot move'
class Car(Vehicle):
name = 'car'
consumption = 100 # (litres per meter)
fuel = 0 # (litres )
def __init__(self, fuel, consumption=None, *args, **kwargs):
self.fuel = fuel
self.consumption = consumption if consumption else self.consumption
super().__init__(*args, **kwargs)
def move(self, distance):
if self.canMove and self.hasFuel():
available_d = self.fuel / self.consumption
if distance <= available_d:
self.fuel -= self.consumption*distance
self.position += distance
return 'The vehicle moved {0} meters and has {1} litres left.'.format(distance, self.fuel)
return 'The vehicle cannot move since it does not have fuel enough'
return 'The vehicle cannot move since it does not have any fuel'
def hasFuel(self):
return True if self.fuel > 0 else False
def giveFuel(self, litres):
self.fuel += litres
If you take some time to read the code, you will see how there are necessary tasks that need to be run in the __init__
method, such as variable assignment, doing checks or running other processes.
Also when you inherit from another class the behaviour gets a bit more complicated. As you see I have to call the mother class with the super().__init__()
call in order to run the rest of the tasks that were being done in it.
__init__
in use
So let's play around with this piece of code I have just created.
You could create your vehicle just like this:
myVehicle = Vehicle()
However that would raise an error, since the __init__
method is requiring to pass one compulsory argument, price
. All the rest are optional fields, but that is obligatory for the instantiation to happen. Therefore you could try again with this:
myVehicle = Vehicle(10000)
You can access the value you have just passed doing:
myVehicle.price
You can also pass the rest of the elements, but they are not obligatory:
myVehicle2 = Vehicle(10000, name='myVehicle2', canMove=True)
Bear in mind that we could also assign them after the instantiation to our first vehicle:
myVehicle.name = 'myVehicle'
So now we have two different vehicles, but one can move and the other can't. We can see this if we run:
myVehicle.move(100)
Whereas myVehicle2.move(100)
won't raise the error. If you change the property of the first vehicle afterwards it will work, regardless of the value you passed to __init__
initially.
It works similar for our Car class. If we do Car()
:
>>> Car()
Traceback (most recent call last):
File "<input>", line 1, in <module>
TypeError: __init__() missing 1 required positional argument: 'fuel'
Even if we do Car(fuel=140)
:
>>> Car(fuel=140)
Traceback (most recent call last):
File "<input>", line 1, in <module>
File "<input>", line 10, in __init__
TypeError: __init__() missing 1 required positional argument: 'price'
All these arguments are defined in the __init__
section, and the price
tag is required because it inherits form the parent class.
Look at how the values work correctly when we try to move our car:
>>> myCar = Car(price=10000, fuel=150, consumption=10)
>>> myCar.move(10)
'The vehicle cannot move since it does not have any fuel' # we actually have not enabled its canMove property
>>> myCar.canMove = True
>>> myCar.move(10)
'The vehicle moved 10 meters and has 50 litres left.'
>>> myCar.move(1)
'The vehicle moved 1 meters and has 40 litres left.'
>>> myCar.move(30)
'The vehicle cannot move since it does not have fuel enough'