Abstract Classes in TypeScript

Last Updated : 19 Sep, 2026

An abstract class in TypeScript acts as a blueprint for related classes and cannot be instantiated directly.

abstract_classes_in_typescript
  • Can contain abstract methods or properties that subclasses must implement.
  • Can contain concrete methods, properties, and constructors with shared functionality.
  • Helps enforce a common structure while allowing subclasses to provide specific implementations.
JavaScript
abstract class Animal {
  abstract makeSound(): void;

  move(): void {
    console.log('Moving...');
  }
}

class Dog extends Animal {
  makeSound(): void {
    console.log('Bark');
  }
}

const myDog = new Dog();
myDog.makeSound();
myDog.move();

Output:

Bark
Moving...
  • Animal defines the abstract makeSound() method and concrete move() method.
  • Dog extends Animal and implements makeSound().
  • The Dog object can use both methods.

Features of Abstract Classes

  • Cannot Be Instantiated: Abstract classes cannot be directly instantiated.
  • Abstract Members: Abstract methods or properties must be implemented by subclasses.
  • Concrete Members: Shared methods and properties can be defined with implementations.
  • Constructors and Properties: Abstract classes can define constructors and properties for shared initialization.
  • Polymorphism: Subclasses can be treated as instances of their abstract base class.

Applications of Abstract Classes

  • Shared Functionality: Define common methods and properties for related classes.
  • Enforcing Implementation: Require subclasses to implement specific members.
  • Code Reuse: Avoid duplicating common functionality across subclasses.
  • Encapsulation: Keep shared logic in a single base class.

More Example of Abstract Classes in TypeScript

Here are some examples:

Example 1: Abstract Class with Abstract Property

Abstract properties require subclasses to provide their own implementation.

JavaScript
abstract class Person {
  abstract name: string;

  display(): void {
    console.log(this.name);
  }
}

class Employee extends Person {
  name: string;
  empCode: number;

  constructor(name: string, code: number) {
    super();
    this.name = name;
    this.empCode = code;
  }
}

const emp = new Employee('James', 100);
emp.display();

Output

James
  • Person declares the abstract name property and concrete display() method.
  • Employee implements name and adds the empCode property.
  • display() is inherited from Person.

Example 2: Abstract Class with Abstract Method

Abstract methods define behavior that each subclass must implement differently.

JavaScript
abstract class Shape {
  abstract getArea(): number;

  printArea(): void {
    console.log(`The area is ${this.getArea()}.`);
  }
}

class Circle extends Shape {
  radius: number;

  constructor(radius: number) {
    super();
    this.radius = radius;
  }

  getArea(): number {
    return Math.PI * this.radius * this.radius;
  }
}

const circle = new Circle(5);
circle.printArea();

Output:

The area is 78.53981633974483.
  • Shape declares the abstract getArea() method.
  • Circle implements getArea() for calculating a circle's area.
  • printArea() provides shared functionality through the abstract base class.

Best Practices

  • Use abstract classes when related classes share common functionality.
  • Use abstract members when subclasses must provide their own implementation.
  • Keep shared logic in concrete methods of the abstract class.
  • Instantiate concrete subclasses rather than the abstract class itself.
Comment

Explore