Concepts / Using super() for Parent Class Access

Using super() for Parent Class Access

A base class defines shared attributes and methods; derived classes inherit from it and add their own specialized features.

  • Programming

One Object, Two Layers

A derived class often needs to do two jobs when an object is created: initialize the information shared by every object in the family, and then initialize information specific to the derived class. A base class provides the shared attributes and methods. The derived class inherits those features and adds specialized ones. The purpose of super() is to let the derived class use the parent implementation instead of copying its work.

base class ofbase class ofSchoolMembername, age, tell()Teachersalary, tell()Studentmarks, tell()
What does a subclass inherit from its base class, and where do subclass-specific features fit?

The Initialization Handoff

When a Teacher object is created, Python begins with Teacher.__init__. The derived initializer first calls the base initializer through super().__init__(name, age). Control moves to SchoolMember.__init__, which initializes the shared name and age attributes. After that call finishes, control returns to Teacher.__init__, where salary is initialized. The important order is shared initialization first, specialized initialization second.

class SchoolMember: def __init__(self, name, age): self.name = name self.age = age print("Initialized SchoolMember:", name) class Teacher(SchoolMember): def __init__(self, name, age, salary): super().__init__(name, age) self.salary = salary print("Initialized Teacher:", name) teacher = Teacher("Mrs. Shrividya", 40, 30000)

callssuper().__init__returns, then continuesTeacher(...)object creationTeacher.__init__receives name, age, salarySchoolMember.__init__sets name, agesalarysets teacher-specific data
When a Teacher is instantiated, how does control move from the subclass initializer to the parent initializer and back?
Output
Initialized SchoolMember: Mrs. Shrividya
Initialized Teacher: Mrs. Shrividya

Extending an Inherited Method

A derived class can redefine a method that already exists in the base class. This is method overriding: the derived version replaces the parent version when the method is called on an object of the derived type. The derived method can either provide completely different behavior or call the parent version first and then add specialized behavior. With super().tell(), Teacher can reuse the shared name-and-age display before adding salary, while Student can reuse the same display before adding marks.

Method designWhat happensSchool example
Inherited unchangedThe derived object uses the base implementationA derived class uses SchoolMember.tell without redefining it
OverriddenThe derived class supplies its own implementationTeacher.tell or Student.tell defines specialized output
Overridden and extendedThe derived method calls the parent implementation and adds behaviorTeacher.tell displays shared details, then salary
python
super().tell() then addsuper().tell() then addSchoolMember.tell()name and ageTeacher.tell()parent details plus salaryStudent.tell()parent details plus marks
How does an unchanged method differ from an override and from an override that calls the parent implementation?

Shared Behavior in a Loop

Teacher and Student each have the shared name and age attributes from SchoolMember, plus their own specialized attribute. Teacher has salary; Student has marks. Both also define tell(), but each version adds different information after using the common SchoolMember behavior.

python
Output
Name: Mrs. Shrividya
Age: 40
Salary: 30000
Name: Asha
Age: 16
Marks: 92

The loop makes the same member.tell() call for both objects. Python uses the appropriate implementation for the object: Teacher.tell() for the Teacher object and Student.tell() for the Student object. This is polymorphism. It lets code work with multiple derived classes without checking whether each object is a Teacher or a Student.

inheritsinheritsaddsaddsSchoolMembername, age, shared tell()Teachersalary, specialized tell()salaryafter shared detailsStudentmarks, specialized tell()marksafter shared details
How can several specialized objects reuse one base class while producing different tell() behavior?

Mistakes with Parent Access

  • Defining a derived __init__ method but skipping the parent initializer

    The shared initialization performed by SchoolMember.__init__ is not called, so the inherited name and age setup is omitted.

    Fix: Call super().__init__(name, age) before setting salary.

  • Replacing a parent method when the intention was to extend it

    This derived implementation does not perform the shared display behavior from SchoolMember.tell().

    Fix: Call super().tell() first, then add the salary-specific output.

  • Copying shared initialization into every derived class

    The shared setup is duplicated rather than defined once in the base class.

    Fix: Keep common attributes in the base initializer and invoke it from each derived initializer.

  • Assuming every object uses exactly the base version of an overridden method

    Teacher and Student define their own tell() methods, so the same call produces type-specific behavior.

    Fix: Remember that the appropriate derived implementation runs for each object.

Put attributes and methods shared by all members in the base class. In each derived class, call the parent initializer for shared setup, then add only the attributes and behavior that make that class specialized.

Practice the Call Order

What do you think happens?

In what order will the initialization messages appear when this object is created?

  • Initialized Teacher, then Initialized SchoolMember
  • Initialized SchoolMember, then Initialized Teacher
  • Only Initialized Teacher
  • Only Initialized SchoolMember
Reveal answer

Answer: Initialized SchoolMember, then Initialized Teacher

Teacher.__init__ calls super().__init__ first. The SchoolMember initializer completes before Teacher continues with its own initialization.

MEDIUM

Create a third derived class named Administrator. Give it a department attribute, initialize the shared name and age through super().__init__, and override tell() so it calls super().tell() before displaying the department.

Hints
  • Make Administrator inherit from SchoolMember.
  • The initializer should receive name, age, and department.
  • The overridden tell() method should call super().tell() before displaying department.

Tracing a Student object

A Student is created with a name, age, and marks. What does the object receive from SchoolMember, and what does Student add?

Start with Student.__init__: The derived initializer receives the shared name and age values together with the Student-specific marks value.

Call the parent initializer: super().__init__(name, age) sends the shared values to SchoolMember.__init__, which initializes name and age.

Add specialized data: Student then initializes marks on the same object.

Call tell(): Student.tell() can call super().tell() for the shared details and then display marks.

The Student object has the inherited name and age attributes plus its own marks attribute, and its tell() method can combine shared and specialized behavior.

Key Takeaways

  1. A base class defines functionality shared by related objects, while a derived class inherits and specializes that functionality.
  2. A derived __init__ method should call the parent initializer through super() so inherited attributes are initialized.
  3. A derived method can override a parent method completely or call super() to extend the parent behavior.
  4. Teacher and Student can share SchoolMember functionality while adding salary and marks respectively.
  5. Polymorphism allows the same member.tell() call to produce the appropriate behavior for each derived object.

Key Takeaways

  • Base classes hold common attributes and methods; derived classes inherit them and add specialized features.
  • Use super().__init__ in a derived initializer to perform the parent class setup before derived-class setup.
  • Use super().method_name() when an overridden method should preserve the parent behavior and add more behavior.
  • Multiple derived classes can share one base implementation while producing different results through polymorphism.