Generics in typescript. What is <T>?

Short tutorial about generics in typescript.

Today we will cover generics in typescript.

Generics

  1. What are generics in general?
  2. How can they be used in typescript?

What are generics in general?

  • Generics are a "generic" way of expressing that something can be used with multiple types.
  • They are often used to save us the time of developing functions multiple times where nothing but the type would change.
  • Once you get to know them, you will probably end up using them a lot as well.
  • Lets approach it with simple examples.
// dummy example of social network.

// a "like" in our social network
interface Like {
  id: string;
}

// a "post" in our social network
interface Post {
  id: string;
  title: string;
}

/** This function removes the last like that was given. */
const removeLastLike = (likes: Like[]): Like[] => {
  if (likes.length === 0) {
    return likes;
  }
  likes.pop();
  return likes;
};

/** This function removes the last post that was posted. */
const removeLastPost = (posts: Post[]): Post[] => {
  if (posts.length === 0) {
    return posts;
  }
  posts.pop();
  return posts;
};

/** As you can see, we have to create two functions to basicly implement
    the same behaviour. For everything we want to remove the last element of in
    an array we would have to create another function with the according type...
    **/

// Generics to the rescue!

/** This function removes the last element from an array. It does not matter
which type of element is inside the array. */
const removeLast = <T>(array: T[]): T[] => {
  if (array.length === 0) {
    return array;
  }
  array.pop();
  return array;
};

const testLikes: Like[] = [{ id: "1" }, { id: "2" }, { id: "3" }];
const testPosts: Post[] = [
  { id: "1", title: "test1" },
  { id: "2", title: "test2" },
  { id: "3", title: "test3" },
];

const resultingPostsNoGenerics1 = removeLastPost(testPosts);
const resultingPostsNoGenerics2 = removeLastPost(testLikes);

const resultingLikes = removeLast<Like>(testLikes);
const resultingPosts = removeLast<Post>(testPosts);
error without generics
When we want to use removeLastPost with testLikes it obviously tells us that the given type is wrong. It did expect an element of type Post[] but got an element of type Likes[].
removeLast with likes working
We don't get an error when we use removeLast<Like> with likes. The <Like> is the generic here. It takes over the type of T and replaces all occurences with Like. Notice how we get a correctly, fully typed function (array: Like[]) which returns Like[].
removeLast with posts working
We don't get an error when we use removeLast<Post> with posts. The <Post> is the generic here. It takes over the type of T and replaces all occurences with Like. Notice how we get a correctly, fully typed function (array: Post[]) which returns Post[].

I hope this did help you understand the usage of generics and generics in typescript.