What is Typescript Map and why it's useful? (With Examples)

In this article I will break down the core functionalities of Typescript Map and why it's a great data-type that you should learn.

what-is-typescript-map-with-examples

Introduction

Understanding Typescript Map is an invaIuable tool in your Developer's arsenal.

In the ever-evolving landscape of web development, understanding the nuances of the tools and languages we use is crucial for creating efficient, scalable, and maintainable applications.

TypeScript, an extension of JavaScript, brings strong typing and object-oriented programming to the forefront, enhancing the development experience and code quality.

Among its many features, the TypeScript Map stands out as a versatile and powerful data structure, essential for developers to master.


In this article, titled "What is a TypeScript Map? (with examples)", I aim to unravel the concept of a Map in TypeScript, a feature that, while often overshadowed by more commonly discussed topics, holds significant potential in optimizing and organizing data within your applications.


Whether you're a seasoned developer or just starting out, understanding Maps in TypeScript is invaluable.

These data structures are not just theoretical concepts but practical tools that can enhance the way you handle data collections in real-world applications.

From managing state in a React application to organizing data sets in server-side logic, TypeScript Maps can be a game-changer.


So, let's embark on this journey to explore the TypeScript Map, its features, and its applications, complete with practical examples to integrate into your next project.

This exploration will not only add a valuable tool to your development toolkit but also align perfectly with the innovative and efficient ethos of PullTheCode.



Basics of TypeScript Map

Defining a TypeScript Map

In TypeScript, a Map is a collection of keyed data items, just like an Object. However, unlike an object, it keeps the order of elements and allows keys of any type.

A Map remembers the original insertion order of the keys, which can be crucial for certain applications.

The basic syntax for creating a Map in TypeScript is as follows:


let map = new Map<KeyType, ValueType>();


Here, KeyType can be any value (e.g., number, string, object), and ValueType represents the type of data you want to store.


Comparison with Other Data Structures

  • Objects: In JavaScript and TypeScript, objects are the standard way to store collections of key-value pairs. However, object keys are limited to strings and symbols. If you use other types as keys, they are converted to strings, which can lead to unexpected results. Maps, on the other hand, can use any type for keys, maintaining the key's type.
  • Sets: A Set is another collection type in JavaScript and TypeScript, but it only stores unique values without any keys. It's more like a list of values rather than a key-value mapping, which is what Maps provide.


Advantages of Using Map

Maps offer several advantages in scenarios where their unique features are needed:

  1. Key Flexibility: Maps allow for keys of any type, not just strings or symbols. This is particularly useful when you need to use objects or other complex types as keys.
  2. Order Preservation: Maps store elements in the order of insertion. This can be important when the order of elements is critical to the application logic.
  3. Size Property: Maps have a size property, which makes it easy to get the number of elements stored in the Map. This is more straightforward than having to calculate the size of an object.
  4. Performance: For larger collections, Maps can perform better than objects when it comes to adding or removing elements, as well as searching for keys.
  5. Direct Iteration: Maps are directly iterable, making it easier to loop over their elements without needing to extract keys first, as you would with an object.


Example Usage

Here's a simple example of creating and using a Map:


let fruitMap = new Map<string, number>();

// Adding key-value pairs
fruitMap.set("apples", 5);
fruitMap.set("bananas", 3);

// Getting a value
console.log(fruitMap.get("apples")); // 5

// Checking for a key
console.log(fruitMap.has("cherries")); // false

// Iterating over Map entries
fruitMap.forEach((value, key) => {
console.log(`${key}: ${value}`);
});


In this example, fruitMap is a Map where each key is a string (the name of a fruit) and each value is a number (the quantity of that fruit).

This showcases the basic operations like adding entries, retrieving values, checking for the presence of keys, and iterating over the Map.



Creating and Initializing a Typescript Map

Creating a New Map

In TypeScript, creating a new Map is straightforward.

You start by declaring a variable and assigning it a new instance of Map.

The generic parameters <KeyType, ValueType> can be specified to enforce type safety.


Here's the basic syntax:

let myMap = new Map<KeyType, ValueType>();


For example, to create a map with string keys and number values:

let myMap = new Map<string, number>();


Initializing a Map with Values

There are several ways to initialize a Map with values


Using the set Method:

After creating a Map, you can add key-value pairs using the set method.

This is useful when you need to add items conditionally or in a loop.


Example:

let bookMap = new Map<string, string>();
bookMap.set("1984", "George Orwell");
bookMap.set("Brave New World", "Aldous Huxley");


Using an Array of Key-Value Pairs

You can also initialize a Map with an array of key-value pairs.

Each key-value pair is an array where the first element is the key and the second is the value.


Example:

let capitalsMap = new Map([
["USA", "Washington, D.C."],
["France", "Paris"],
["Japan", "Tokyo"]
]);


Copying from Another Typescript Map

If you already have a Map and want to create a new one with the same values, you can pass the existing Map to the constructor of the new Map.


Example:

let originalMap = new Map([
["apple", 1],
["banana", 2]
]);

let clonedMap = new Map(originalMap);


From Other Iterable Objects

TypeScript Maps can also be initialized from other iterable objects (like Arrays or other Maps) that yield key-value pairs.

let keyValueArray = [["key1", "value1"], ["key2", "value2"]];
let iterableMap = new Map(keyValueArray);


Example: Initializing a Map with Dynamic Data

Consider a scenario where you're initializing a Map with data fetched from an API:


// Assume this data comes from an API
let userData = [
{ id: 1, name: "Alice" },
{ id: 2, name: "Bob" }
];

let userMap = new Map<number, string>();
userData.forEach(user => userMap.set(user.id, user.name));


In this example, userMap is a Map where each key is a user ID (number) and each value is the user's name (string).

This demonstrates how Maps can be dynamically populated with data, making them highly versatile in real-world applications.



Working with Keys and Values in a TypeScript Map

Adding Values to a Map

To add key-value pairs to a Map, use the set method.

This method takes two arguments: the key and the value.

If the key already exists in the Map, its value will be updated.

Otherwise, a new key-value pair is added.


let colorMap = new Map<string, string>();
colorMap.set("red", "#FF0000");
colorMap.set("green", "#00FF00");
colorMap.set("blue", "#0000FF");


In this example, colorMap stores color names as keys and their hexadecimal codes as values.


Retrieving Values from a Typescript Map

To retrieve a value from a Map, use the get method with the key as its argument.

If the key is present in the Map, get returns its value; otherwise, it returns undefined.


let greenHex = colorMap.get("green"); // "#00FF00"
let purpleHex = colorMap.get("purple"); // undefined

Here, greenHex retrieves the value for the key "green", while purpleHex results in undefined since "purple" is not a key in the Map.


Updating Values in a Typescript Map

Updating a value in a Map is similar to adding a value.

Use the set method with the existing key and the new value.

This will overwrite the previous value associated with that key.


colorMap.set("red", "#FF5733"); // Update the value for the key "red"


In this example, the value for the key "red" is updated to a different shade.


Uniqueness of Keys

A key feature of Maps is that each key is unique.

If you set a new value for an existing key, the Map doesn't create a new key but updates the existing key's value.

This ensures that each key maps to exactly one value.


colorMap.set("blue", "#1E90FF");
console.log(colorMap.get("blue")); // "#1E90FF"


After updating, the key "blue" now maps to a new value, demonstrating the uniqueness and update-in-place nature of Map keys.


Code Examples: Adding, Retrieving, and Updating

Here's a comprehensive example demonstrating these operations:

let bookRatings = new Map<string, number>();

// Adding values
bookRatings.set("1984", 4.5);
bookRatings.set("Brave New World", 4.0);

// Retrieving a value
let rating1984 = bookRatings.get("1984"); // 4.5

// Updating a value
bookRatings.set("1984", 4.7); // Update the rating for "1984"

// Attempting to retrieve a non-existent key
let ratingGatsby = bookRatings.get("The Great Gatsby"); // undefined

In this example, bookRatings is a Map that stores book titles as keys and their ratings as values.

It demonstrates adding new entries, retrieving values, updating an existing entry, and the behavior when attempting to retrieve a value for a non-existent key.




Working with Keys and Values in a TypeScript Map

Adding Values to a Map

To add key-value pairs to a Map, use the set method.

This method takes two arguments: the key and the value.

If the key already exists in the Map, its value will be updated.

Otherwise, a new key-value pair is added.


let colorMap = new Map<string, string>();
colorMap.set("red", "#FF0000");
colorMap.set("green", "#00FF00");
colorMap.set("blue", "#0000FF");


In this example, colorMap stores color names as keys and their hexadecimal codes as values.


Retrieving Values from a Map

To retrieve a value from a Map, use the get method with the key as its argument.

If the key is present in the Map, get returns its value; otherwise, it returns undefined.


let greenHex = colorMap.get("green"); // "#00FF00"
let purpleHex = colorMap.get("purple"); // undefined


Here, greenHex retrieves the value for the key "green", while purpleHex results in undefined since "purple" is not a key in the Map.


Updating Values in a Map

Updating a value in a Map is similar to adding a value.

Use the set method with the existing key and the new value.

This will overwrite the previous value associated with that key.


colorMap.set("red", "#FF5733"); // Update the value for the key "red"


In this example, the value for the key "red" is updated to a different shade.


Uniqueness of Keys

A key feature of Maps is that each key is unique.

If you set a new value for an existing key, the Map doesn't create a new key but updates the existing key's value.

This ensures that each key maps to exactly one value.


colorMap.set("blue", "#1E90FF");
console.log(colorMap.get("blue")); // "#1E90FF"


After updating, the key "blue" now maps to a new value, demonstrating the uniqueness and update-in-place nature of Map keys.


Code Examples: Adding, Retrieving, and Updating

Here's a comprehensive example demonstrating these operations:


const bookRatings = new Map<string, number>();

// Adding values
bookRatings.set("1984", 4.5);
bookRatings.set("Brave New World", 4.0);

// Retrieving a value
const rating1984 = bookRatings.get("1984"); // 4.5

// Updating a value
bookRatings.set("1984", 4.7); // Update the rating for "1984"

// Attempting to retrieve a non-existent key
const ratingGatsby = bookRatings.get("The Great Gatsby"); // undefined


In this example, bookRatings is a Typescript Map that stores book titles as keys and their ratings as values.

It demonstrates adding new entries, retrieving values, updating an existing entry, and the behavior when attempting to retrieve a value for a non-existent key.



Iterating Over a Map in TypeScript

Maps in TypeScript are iterable, which means you can easily loop through them to access their keys and values.

There are several ways to iterate over a Map, including using for...of loops and the forEach method.


Iterating Over Keys and Values Using for...of

The for...of loop is a straightforward way to iterate over a Map.

You can loop over the Map's entries, keys, or values depending on your needs.


Iterating Over Entries (Key-Value Pairs)

let colorMap = new Map([
["red", "#FF0000"],
["green", "#00FF00"],
["blue", "#0000FF"]
]);

for (let [key, value] of colorMap) {
console.log(`Key: ${key}, Value: ${value}`);
}


This loop iterates over each entry in the colorMap, logging both the key and the value.


Iterating Over Keys

for (let key of colorMap.keys()) {
console.log(`Key: ${key}`);
}


This loop iterates over the keys of the colorMap.


Iterating Over Values

for (let value of colorMap.values()) {
console.log(`Value: ${value}`);
}


This loop iterates over the values of the colorMap.


Using the forEach Method

The forEach method is another way to iterate over a Map.

It takes a callback function that is executed for each key-value pair in the Map.


colorMap.forEach((value, key) => {
console.log(`Key: ${key}, Value: ${value}`);
});


In this example, the forEach method is used to log the key and value of each entry in the colorMap.

Note that the order of parameters in the callback function is value followed by key, which is a bit different from the for...of loop where the key comes first.


Example: Iterating Over a Map with Complex Data

Consider a Map that stores user IDs as keys and user objects as values.

Here's how you can iterate over such a Map:


let userMap = new Map<number, { name: string, age: number }>([
[1, { name: "Alice", age: 30 }],
[2, { name: "Bob", age: 25 }]
]);

// Iterating over entries
for (let [id, user] of userMap) {
console.log(`User ID: ${id}, Name: ${user.name}, Age: ${user.age}`);
}

// Using forEach
userMap.forEach((user, id) => {
console.log(`User ID: ${id}, Name: ${user.name}, Age: ${user.age}`);
});


In this example, both for...of and forEach are used to iterate over the userMap, demonstrating how to handle Maps with more complex data structures.



Advanced Features of TypeScript Maps

Ordering and Size Properties

One of the advanced features of TypeScript Maps is their inherent order.

Unlike objects, which have no guaranteed order for their properties, Maps maintain the order of elements as they are inserted.

This feature can be particularly useful when the order of data matters in your application logic.


Additionally, Maps have a size property, which provides an immediate count of the number of elements in the Map.

This is more efficient than having to manually count entries, as you might with an object.


let userMap = new Map<string, string>();
userMap.set("user1", "Alice");
userMap.set("user2", "Bob");

console.log(userMap.size); // Output: 2


In this example, the size property quickly tells us that there are two entries in the userMap.


WeakMap: A Related Concept

WeakMap is a variant of Map that allows for a more flexible garbage collection.

In a WeakMap, keys are only weakly held, meaning if there is no other reference to the key stored outside the WeakMap, they can be garbage collected.

This is particularly useful in scenarios where you want to avoid memory leaks, especially in large applications.


let weakMap = new WeakMap<object, string>();
let obj = {};

weakMap.set(obj, "Some data");

// If obj is set to null, the entry in weakMap can be garbage collected
obj = null;


In this example, once there are no more references to obj, the garbage collector can free the memory used by the key-value pair in weakMap.



Practical Application in Web Development

In web development, especially in complex applications, managing memory efficiently is crucial.

WeakMap provides a way to associate data with objects without preventing those objects from being garbage-collected.

This can be particularly useful in scenarios like caching data from a server or managing references to DOM elements in a large single-page application (SPA).


Leveraging Map Order in UI Components

The order preservation feature of Maps can be leveraged in UI components.

For instance, when rendering a list of items in a React component, a Map can ensure that the order of items remains consistent, which can be important for user experience or when the order carries specific meaning.


// Example in a React component
const MyComponent = () => {
const itemMap = new Map<number, string>([
[1, "Item 1"],
[2, "Item 2"],
[3, "Item 3"]
]);

return (
<ul>
{[...itemMap.entries()].map(([id, name]) => (
<li key={id}>{name}</li>
))}
</ul>
);
};


In this React component, itemMap is used to render a list of items in the order they were added to the Map.



Conclusion and Further Resources

Wrapping Up

Throughout this article, we've explored the versatile and powerful TypeScript Map, a data structure that offers unique advantages in web development.

We began by defining what a Map is and how it compares to other data structures like Objects and Sets.

We then delved into creating and initializing Maps, followed by detailed discussions on working with keys and values, and iterating over Maps.

We highlighted the advanced features of Maps, such as their inherent order and size properties, and introduced the concept of WeakMap for scenarios requiring more flexible memory management.

Finally, we provided a practical example of using Maps in state management within a React application, demonstrating their real-world applicability in projects that PullTheCode's audience might undertake.


Encouragement to Experiment

Maps in TypeScript are a powerful tool that can significantly enhance your coding projects, especially when dealing with complex data structures or state management scenarios.

We encourage you to experiment with Typescript Maps in your projects.

Their flexibility, efficiency, and ease of use make them an excellent choice for various applications, from simple scripts to complex web applications.


Further Resources

To deepen your understanding and skills in using TypeScript Maps, here are some resources for further exploration:

  1. TypeScript Official Documentation: Dive into the official TypeScript documentation for a comprehensive understanding of TypeScript features, including Maps.
  2. MDN Web Docs: For a deeper look into JavaScript Maps, which are the foundation of TypeScript Maps, visit MDN's Map documentation.
  3. TypeScript Deep Dive: An excellent resource for all things TypeScript, including Maps, is the TypeScript Deep Dive book by Basarat Ali Syed.
  4. Interactive TypeScript Tutorials: Platforms like Codecademy and TypeScript Exercises offer interactive tutorials where you can practice TypeScript, including working with Maps.


By utilizing these resources, you can further enhance your understanding and proficiency in using TypeScript Maps, making your journey in web development more efficient and your applications more robust.

Own your own Software!

Join PullTheCode and start building your own SaaS in minutes on a platform you own!

Get PullTheCode