Classes in TypeScript: Constructors and Members

Table of Contents

  • Introduction
  • Understanding Classes in TypeScript
    • What is a Class?
    • Defining a Basic Class
  • Class Members: Properties and Methods
    • Defining Properties
    • Defining Methods
    • Access Modifiers: Public, Private, and Protected
  • The Constructor Method in TypeScript
    • What is a Constructor?
    • Using Constructors for Initialization
    • Constructor Overloading
  • Static Members in Classes
  • Inheritance in TypeScript Classes
  • Practical Examples of Classes
  • Conclusion

Introduction

In TypeScript, classes are a blueprint for creating objects with shared properties and methods. They provide a way to model real-world entities in code and are a core concept in object-oriented programming (OOP). TypeScript enhances JavaScript’s class capabilities with strong typing, access modifiers, and other features, making it a powerful tool for building scalable and maintainable applications.

In this article, we’ll dive deep into classes in TypeScript, focusing on constructors, members (properties and methods), and other key aspects of class design.


Understanding Classes in TypeScript

What is a Class?

A class is a blueprint for creating objects. It defines the properties and methods that objects created from the class will have. Classes are a central feature of object-oriented programming (OOP) and are used to group data and functions together.

In TypeScript, the class syntax is similar to ES6 JavaScript classes, but with the added benefit of type checking.

Defining a Basic Class

Here’s how you define a simple class in TypeScript:

class Person {
name: string;
age: number;

constructor(name: string, age: number) {
this.name = name;
this.age = age;
}

greet() {
console.log(`Hello, my name is ${this.name} and I am ${this.age} years old.`);
}
}

const person = new Person("John", 30);
person.greet(); // Output: Hello, my name is John and I am 30 years old.

In this example:

  • We define a Person class with two properties: name and age.
  • We define a constructor to initialize these properties.
  • We define a method greet() that prints a message.

Class Members: Properties and Methods

Classes in TypeScript can have various members, including properties (data) and methods (functions). These members can be public, private, or protected, depending on their access level.

Defining Properties

In TypeScript, properties in a class are defined just like variables, but with explicit types. For example:

class Person {
name: string;
age: number;

constructor(name: string, age: number) {
this.name = name;
this.age = age;
}
}

In this example, name is a string and age is a number.

You can also define optional properties using the ? syntax:

class Person {
name: string;
age: number;
nickname?: string; // Optional property

constructor(name: string, age: number, nickname?: string) {
this.name = name;
this.age = age;
if (nickname) {
this.nickname = nickname;
}
}
}

Defining Methods

Methods inside a class are defined like functions, and they operate on the class’s properties. Here’s an example:

class Person {
name: string;
age: number;

constructor(name: string, age: number) {
this.name = name;
this.age = age;
}

introduce(): void {
console.log(`Hi, I'm ${this.name} and I am ${this.age} years old.`);
}
}

const person = new Person("Alice", 25);
person.introduce(); // Output: Hi, I'm Alice and I am 25 years old.

Access Modifiers: Public, Private, and Protected

TypeScript provides three access modifiers to control the visibility of properties and methods:

  • public: The member is accessible from anywhere (default).
  • private: The member is only accessible within the class.
  • protected: The member is accessible within the class and its subclasses.

Example: Using Access Modifiers

class Person {
public name: string;
private age: number;
protected address: string;

constructor(name: string, age: number, address: string) {
this.name = name;
this.age = age;
this.address = address;
}

public greet(): void {
console.log(`Hello, my name is ${this.name}.`);
}

private calculateAgeInMonths(): number {
return this.age * 12;
}

protected updateAddress(newAddress: string): void {
this.address = newAddress;
}
}

In this example:

  • name is public and can be accessed from anywhere.
  • age is private and can only be accessed within the Person class.
  • address is protected and can be accessed within the Person class and any derived classes.

The Constructor Method in TypeScript

The constructor is a special method that is called when a class is instantiated (i.e., when an object is created from the class). It is used to initialize the object’s properties.

What is a Constructor?

The constructor method is declared with the constructor keyword, followed by parameters and the this keyword to assign values to the object’s properties.

Example: Basic Constructor

class Person {
name: string;
age: number;

constructor(name: string, age: number) {
this.name = name;
this.age = age;
}
}

const person = new Person("John", 30);
console.log(person.name); // Output: John
console.log(person.age); // Output: 30

Using Constructors for Initialization

You can use the constructor to initialize properties when creating an object. If a property is required to be initialized on object creation, it can be added as a constructor parameter.

Example: Constructor with Optional Parameters

class Person {
name: string;
age: number;
city?: string;

constructor(name: string, age: number, city?: string) {
this.name = name;
this.age = age;
if (city) {
this.city = city;
}
}
}

const person = new Person("Jane", 28, "New York");
console.log(person.city); // Output: New York

Constructor Overloading

TypeScript doesn’t support traditional constructor overloading as seen in other languages like Java or C#. However, you can mimic constructor overloading by using optional parameters or union types.

Example: Constructor Overloading with Optional Parameters

class Person {
name: string;
age: number;

constructor(name: string, age: number);
constructor(name: string);
constructor(name: string, age?: number) {
this.name = name;
this.age = age ?? 0; // Default value if age is not provided
}

introduce() {
console.log(`Hi, I am ${this.name} and I am ${this.age} years old.`);
}
}

const person1 = new Person("John", 30);
person1.introduce(); // Output: Hi, I am John and I am 30 years old.

const person2 = new Person("Alice");
person2.introduce(); // Output: Hi, I am Alice and I am 0 years old.

Static Members in Classes

Static members belong to the class itself, rather than instances of the class. This means they are shared across all instances of the class.

Example: Using Static Members

class Calculator {
static pi: number = 3.14159;

static calculateArea(radius: number): number {
return Calculator.pi * radius * radius;
}
}

console.log(Calculator.pi); // Output: 3.14159
console.log(Calculator.calculateArea(5)); // Output: 78.53975

In this example, the pi property and calculateArea() method are static and are accessed directly from the class.


Inheritance in TypeScript Classes

TypeScript supports inheritance, allowing one class to inherit properties and methods from another.

Example: Inheritance

class Animal {
name: string;

constructor(name: string) {
this.name = name;
}

speak() {
console.log(`${this.name} makes a sound.`);
}
}

class Dog extends Animal {
constructor(name: string) {
super(name); // Calling the parent class constructor
}

speak() {
console.log(`${this.name} barks.`);
}
}

const dog = new Dog("Rex");
dog.speak(); // Output: Rex barks.

In this example:

  • Dog extends Animal, inheriting its properties and methods.
  • speak() is overridden in the Dog class to provide a more specific implementation.

Practical Examples of Classes

Example 1: Building a Simple Bank Account

class BankAccount {
private balance: number;

constructor(initialBalance: number) {
this.balance = initialBalance;
}

deposit(amount: number): void {
this.balance += amount;
}

withdraw(amount: number): void {
if (amount <= this.balance) {
this.balance -= amount;
} else {
console.log("Insufficient funds.");
}
}

getBalance(): number {
return this.balance;
}
}

const account = new BankAccount(1000);
account.deposit(500);
account.withdraw(200);
console.log(account.getBalance()); // Output: 1300

In this example, the BankAccount class has methods to deposit and withdraw money, while keeping the balance property private.


Conclusion

Classes are a fundamental building block in TypeScript, providing a structured and type-safe way to create objects. In this article, we’ve explored the key concepts of constructors and members in TypeScript classes, including how to define properties, methods, and static members. We’ve also covered important topics such as inheritance and access modifiers.

Understanding how to use classes effectively allows you to write more organized, maintainable, and robust TypeScript code.