Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is a constructor __init__ necessary for a class in Python?

I read that the constructor is like the first argument passed to the class, which makes sense to me since the parameters seem to be passed to the class via the __init__ method. For example,

class NewsStory(object):
    def __init__(self, guid, title, subject, summary, link):
        self.guid = guid
        self.title = title
        self.subject = subject
        self.summary = summary
        self.link = link

    def get_guid(self):
        return self.guid

    def get_title(self):
        return self.title

    def get_subject(self):
        return self.subject

    def get_summary(self):
        return self.summary

    def get_link(self):
        return self.link
firstStory = NewsStory('Globally Unique Identifier', \
    'first_title','first_subject','This is an example \
    sumary','[email protected]')

print firstStory.get_guid() # prints Globally Unique Identifier

So when I 'call' the class, I pass it the parameters from the __init__ method? I'm new to classes, everything I read I find hard to understand and confusing. Thanks!

Edit 1

I found this question helpful in explaining some things, like the difference between new and init, sorry, I don't know how to add a link, gotta cut and paste: What can `__init__` do that `__new__` cannot?

like image 342
sampy Avatar asked Jul 09 '16 09:07

sampy


2 Answers

I see a misconception here between a constructor--constructing the object and initializing the object:

Python's use of __new__ and __init__?

Use __new__ when you need to control the creation of a new instance. Use __init__ when you need to control initialization of a new instance.

So we must be careful here.

I read that the constructor is like the first argument passed to the class, which makes sense to me since the parameters seem to be passed to the class via the __init__ method.

The constructor is not passed to the class, to be precise the result of the constructor (__new__) will be the first argument for every instance method in the class or its sub-classes (note: __new__ works only for new-style classes):

class A:
    def __new__(self):
            return 'xyz'

See what happens when you call the class (create the object):

>>> A()
'xyz'
>>> type(A())
<class 'str'>

Calling the class no longer return instance of type A, because we changed the mechanism of the constructor __new__. Actually by doing so you alter the whole meaning of your class, not only, this is pretty much hard to decipher. It's unlikely that you'll switch the type of object during the creating time of that specific object. I hope this sentence makes sense, if not, how will it make sense in your code!

class A:
    def __new__(self):
            return 'xyz'

    def type_check(self):
            print(type(self))

Look what happens when we try to call type_check method:

>>> a = A()
>>> a
'xyz'
>>> a.type_check()
AttributeError: 'str' object has no attribute 'type_check'

a is not an object of class A, so basically you don't have access to class A anymore.

__init__ is used to initialize the object's state. Instead of calling methods that will initialize the object's members after it's created, __init__ solves this issue by initializing the object's members during creation time, so if you have a member called name inside a class and you want to initialize name when you create the class instead of calling an extra method init_name('name'), you would certainly use __init__ for this purpose.

So when I 'call' the class, I pass it the parameters from the __init__ method?

When you call the class, you pass the parameters (to) __init__ method?

Whatever arguments you pass the class, all the parameters will be passed to __init__ with one additional parameter added automatically for you which is the implied object usually called self (the instance itself) that will be passed always as the left-most argument by Python automatically:

class A:
    def __init__(self, a, b):
        self.a = a
        self.b = b 

        A(  34,  35) 
 self.a = 34 |    |  
             |    | 
             |    | self.b = 35  
  init(self, a,   b)
        |
        |
        | 
       The instance that you created by calling the class A() 

Note: __init__ works for both classic classes and new style classes. Whereas, __new__ works only for new-style classes.

like image 194
direprobs Avatar answered Nov 10 '22 09:11

direprobs


No, the constructor is just the method that is called to construct the object. It is not passed anywhere. Rather the object itself is passed automatically to all methods of the class.

Constructor is not required if you don't have anything to construct but usually you have something to do in the beginning.

like image 21
Sami Kuhmonen Avatar answered Nov 10 '22 09:11

Sami Kuhmonen