Dee
Dee

Reputation: 91

Python child instance property appears to be overridden by parent property

I'm in the process of learning Python 3 and writing conceptual bits of code to aid my understanding. I hit a problem with a simple class inheritance example where an instance variable from the child class appears to be overridden by the parent variable.

I've played around with the following code in various forms and have simplified it for the purpose of this question. I can't figure out why the Child object's own __str__() method is referring to the name property of the Parent when I am using self.name inside the Child class to refer to the name property of the Child (it's as if self.name is replaced with super().name).

class Parent():

    """ Parent class that will take a name or default to 'Default Parent'.
    """

    def __init__(self, name="Default Parent"):
        self.name = name

    def __str__(self):
        return f'Parent: I am {self.name}'

class Child(Parent):

    """ Child class inheriting from Parent class
    """

    def __init__(self, name="Default Child"):
        # setting self.name to the name passed in during Child instantiation
        self.name = name
        # not passing self.name so parents's self.name will be defaulted to "Default Parent"
        super().__init__() 

    def __str__(self):
        # self.name prints "Default Parent"
        # The property self.name in Child appears to be overridden.
        # Thought self.name here refers to the instant variable belonging to the instance of Child and not super().name.
        return f'Child: I am {self.name}'

I've tested this as follows:

p1 = Parent("Parent 1")
c1 = Child("Child 1")
print(p1)
print(c1)

I expected these results back:

Parent: I am Parent 1
Child: I am Child 1

Instead, I got these back:

Parent: I am Parent 1
Child: I am Default Parent

Upvotes: 0

Views: 436

Answers (1)

James
James

Reputation: 36598

You are calling super().__init__() after you set the self.name in Child. This is overwriting the property. Instead, pass the name parameter to the parent init.

class Child(Parent):

    """ Child class inheriting from Parent class
    """

    def __init__(self, name="Default Child"):
        super().__init__(name=name) 

Upvotes: 1

Related Questions