Back to JavaScript
2026-05-068 min read

Extends and inheritance (JavaScript)

Learn Extends and inheritance (JavaScript) step by step with clear examples and exercises.

Title: Extends and Inheritance (JavaScript)

Why This Matters

In JavaScript, classes are used to create objects with a specific structure and behavior. However, when we need to reuse code across multiple classes or create a hierarchy of related classes, we can use the concepts of extends and inheritance. This allows us to avoid redundancy and maintain a clean, organized codebase. Understanding these concepts is crucial for creating efficient, scalable applications in JavaScript.

Prerequisites

Before diving into extends and inheritance, you should be familiar with the following topics:

  1. JavaScript basics: variables, data types, operators, functions, and control structures
  2. Objects and properties in JavaScript
  3. Classes and constructors in JavaScript (optional but recommended)
  4. Understanding the prototype chain in JavaScript
  5. Understanding how this works in JavaScript classes

Core Concept

Defining a Superclass (Base Class)

To create a superclass or base class, we define a regular JavaScript function with a constructor method and properties. Here's an example of a Vehicle superclass:

function Vehicle(make, model, year) {
this.make = make;
this.model = model;
this.year = year;
}

Creating a Subclass (Derived Class) and Inheriting Properties

To create a subclass or derived class that inherits properties from the superclass, we use the extends keyword followed by the name of the superclass constructor function. Here's an example of a Car subclass that extends the Vehicle superclass:

function Car(make, model, year, numDoors) {
// Call the parent (super) constructor using 'super' keyword
super(make, model, year);
this.numDoors = numDoors;
}

// Inherit prototype methods from Vehicle
Car.prototype = Object.create(Vehicle.prototype);

In the example above, we call the super() function in the constructor of the Car class to initialize its properties inherited from the Vehicle superclass. We also set the prototype of the Car class to inherit methods from the Vehicle prototype object.

Overriding Methods and Properties

We can override methods or properties defined in the superclass by redefining them in the subclass. For example, if we want to add a method called startEngine() to our Car class, we can do it like this:

function Car(make, model, year, numDoors) {
// Call the parent (super) constructor using 'super' keyword
super(make, model, year);
this.numDoors = numDoors;
}

Car.prototype.startEngine = function() {
console.log('Engine started');
};

In this example, we have overridden the default behavior of the startEngine() method defined in the Vehicle superclass (if any).

Accessing Superclass Methods and Properties

To access a method or property from the superclass within the subclass, we can use the super keyword. For example:

function Car(make, model, year, numDoors) {
// Call the parent (super) constructor using 'super' keyword
super(make, model, year);
this.numDoors = numDoors;
}

Car.prototype.startEngine = function() {
console.log('Engine started');
console.log(`Make: ${this.make}`); // Accessing superclass property
};

Understanding the Prototype Chain

The prototype chain plays a crucial role in inheritance in JavaScript. When you access a property or method on an object, JavaScript first looks for that property or method on the object itself. If it's not found, JavaScript then looks up its parent objects in the prototype chain until it finds the property or method. In our example above, the Car class inherits methods from the Vehicle class through the prototype chain.

Understanding the this Keyword

In JavaScript classes, the this keyword refers to the instance of the class that is being created. Inside a constructor function, this refers to the newly created object. In the example above, when we call super(make, model, year), this inside the Vehicle constructor refers to the new Car instance.

Worked Example

Let's create a simple example with a Vehicle superclass and two subclasses, Car and Bike.

function Vehicle(make, model, year) {
this.make = make;
this.model = model;
this.year = year;
}

Vehicle.prototype.drive = function() {
console.log(`Driving a ${this.make} ${this.model}`);
};

function Car(make, model, year, numDoors) {
super(make, model, year);
this.numDoors = numDoors;
}

Car.prototype.startEngine = function() {
console.log('Engine started');
};

Car.prototype.drive = function() {
console.log(`Driving a ${this.make} ${this.model} with ${this.numDoors} doors`);
};

function Bike(make, model, year, numWheels) {
super(make, model, year);
this.numWheels = numWheels;
}

Bike.prototype.ringBell = function() {
console.log('Ring ring');
};

// Create instances of Car and Bike classes
const myCar = new Car('Toyota', 'Corolla', 2021, 4);
const myBike = new Bike('Honda', 'CBR600', 2020, 2);

// Call methods on instances
myCar.startEngine();
myCar.drive();
myBike.ringBell();

In this example, we have created a Vehicle superclass and two subclasses, Car and Bike. The Car class overrides the default behavior of the drive() method from the Vehicle superclass and adds a new method called startEngine() to the Car class. We also added a new method called ringBell() to the Bike class. We then create instances of both classes and call their methods.

Common Mistakes

  1. Forgetting to call super() in the subclass constructor: If you forget to call super() in the subclass constructor, the properties inherited from the superclass will not be initialized correctly.
  2. Not setting the prototype of the subclass: To inherit methods from the superclass, we must set the prototype of the subclass to inherit from the superclass's prototype object.
  3. Overriding methods without understanding their purpose: Be careful when overriding methods in the subclass, as it may break the intended behavior of the superclass or other parts of your application.
  4. Accessing undefined properties or methods: Ensure that all properties and methods are defined before trying to access them, either in the current class or its parent classes.
  5. Mixing up super and this keywords: Be aware of the differences between super and this keywords, as they have different scopes and purposes within JavaScript classes.
  6. Not understanding the prototype chain: Understanding how the prototype chain works is essential for working with inheritance in JavaScript. Make sure you understand how objects and their properties are linked together through the prototype chain.
  7. Using Object.create() incorrectly: When creating a subclass, it's important to use Object.create(superClass.prototype) instead of new superClass() to set the prototype correctly.
  8. Not overriding all necessary methods: If you want your subclass to behave exactly like its superclass but with some additional functionality, make sure you override all necessary methods in the subclass.
  9. Forgetting to call super.constructor() when using Object.create(): When creating a subclass using Object.create(superClass.prototype), you might need to call super.constructor(arguments...) to initialize properties inherited from the superclass constructor.
  10. Not handling the constructor property correctly: In JavaScript, each constructor function has a constructor property that points back to itself by default. When creating a subclass, make sure you handle this property correctly to maintain proper inheritance.

Practice Questions

  1. Create a Person superclass with properties for name, age, and occupation. Then create a Student subclass that extends Person and adds properties for enrollment year and GPA. Override the toString() method to display all properties of a Student instance.
  2. Given the following classes:
function Animal(name, age) {
this.name = name;
this.age = age;
}

function Cat(name, age, breed) {
Animal.call(this, name, age);
this.breed = breed;
}

Create a Dog class that extends the Animal class and adds properties for breed and number of legs. Override the toString() method to display all properties of a Dog instance.

FAQ

What is the purpose of the super keyword in JavaScript classes?

The super keyword allows us to call methods and access properties defined in the superclass within the subclass.

Can I extend multiple classes in JavaScript?

Yes, you can use the Object.create() method to create a prototype object that inherits from multiple classes. However, keep in mind that JavaScript does not have native support for multiple inheritance like some other languages do.

What happens if I forget to call super() in the subclass constructor?

If you forget to call super() in the subclass constructor, the properties inherited from the superclass will not be initialized correctly. This can lead to undefined behavior or runtime errors.

How do I access a method defined in the superclass within the subclass?

To access a method defined in the superclass within the subclass, use the super keyword followed by the method name (e.g., super.methodName()).

Can I override a static method from the superclass in the subclass?

No, you cannot override static methods in JavaScript because they are not part of the prototype chain and are defined directly on the constructor function itself. Instead, you can create new static methods in the subclass that shadow (hide) the same-named methods in the superclass.

How does the prototype chain work in JavaScript classes?

In JavaScript classes, each object has a prototype property that points to another object (or null). When you access a property or method on an object, JavaScript first looks for that property or method on the object itself. If it's not found, JavaScript then looks up its parent objects in the prototype chain until it finds the property or method.

What is the difference between this and super keywords in JavaScript classes?

In JavaScript classes, this refers to the instance of the class that is being created. Inside a constructor function, this refers to the newly created object. The super keyword allows us to call methods and access properties defined in the superclass within the subclass.

How do I create a new instance of a subclass using Object.create()?

To create a new instance of a subclass using Object.create(), you should pass the prototype object of the subclass (i.e., subClass.prototype) as the first argument and an optional second argument for properties to initialize on the new instance. For example:

const myInstance = Object.create(subClass.prototype, {myProperty: {value: 'some value'}});

How do I handle the constructor property correctly when creating a subclass?

In JavaScript, each constructor function has a constructor property that points back to itself by default. When creating a subclass, you should override the constructor property in the subclass to point to the constructor of the superclass. For example:

function SubClass() {
// Call the parent (super) constructor using 'super' keyword
super();
// Add any additional properties or methods here
}

SubClass.prototype = Object.create(SuperClass.prototype);
SubClass.prototype.constructor = SubClass;

How do I handle the constructor property correctly when creating a subclass using Object.create()?

When creating a subclass using Object.create(superClass.prototype), you should set the constructor property of the new object to the constructor function of the subclass. For example:

const SubClass = function() {
// Add any additional properties or methods here
};

SubClass.prototype = Object.create(SuperClass.prototype);
SubClass.prototype.constructor = SubClass;

const myInstance = new SubClass();
Extends and inheritance (JavaScript) | JavaScript | XQA Learn