Learn TypeScript

Creating generic functions

Creating generic functions

In this lesson, we will learn how to create strongly-typed functions with the parameter and return types flexible.

A non-generic function

Below is a function that takes in an array and returns its first element. If the array is empty, then null is returned.

function firstOrNull(array: string[]): string | null {
return array.length === 0 ? null : array[0];
}

This function is strongly-typed, which is excellent, but what if we need to do the same thing for an array of numbers? We can't use the above function because it is restricted for arrays of strings. Wouldn't it be nice if we could pass the array item type into this function? Well, this is what generic functions allow us to.

Generic function syntax

We define the type parameters for a generic function in angled-brackets before the function's parentheses:

function someFunc<T1, T2, ...>(...) {
...
}

Generic parameters can be passed into arrow functions as well:

const someVar = <T1, T2, ...>(...) => {
...
}

The type parameters are placeholders for the real types. We can choose any names we want for these. These type parameter names can then be referenced within the function implementation.

You will often see names T and S used for the type parameters in TypeScript code. Here are some of the common names that are used and what they are used for:

  • T (for "T"ype)
  • S (for "S"ate)
  • E (for "E"lement)
  • K (for "K"ey)
  • V (for "V"alue)

Creating a generic function

Let's turn our attention back to the function, firstOrNull, from the start of this lesson which is in the code exercise below:

TypeScriptOpen exercise in CodeSandbox

We are going to convert this into a generic function. We want to call this function and pass in the array item type as follows:

firstOrNull<string>(["Rod", "Jane", "Fred"]);
firstOrNull<number>([1, 2, 3]);

So, firstOrNull needs a single generic parameter. Let's call this T.

  • Add the generic parameter to the firstOrNull function.
  • Reference T for the array type in the function parameter and return type.

Great, our function is now generic and strongly-typed.

Type inference on generic functions

Does type inference work on our generic functions? Let's find out:

  • Let's call our firstOrNull function without passing the array item types in the generic parameter:
const first = firstOrNull([1, 2, 3]);
console.log(first);
🤔

What is the inferred type of first?

TypeScript can cleverly infer the return type of a generic function if its parameters are based on the generic type.

Summary

Using generic types in a function allows them to be strongly-typed but still be used with different types. The generic types can be referenced within the function's parameters, implementation, and return type.

Next up, we’ll learn how we can use generics to create reusable interfaces.

Did you find this lesson useful?

Share this lesson on twitter
© 2023 Carl Rippon
Privacy Policy
This site uses cookies. Click here to find out more