Includes


Problem - On Github

The aim for this challenge is to take an array and a value, and return whether that value appears in the array.

The initial type is:

type Includes<T extends readonly any[], U> = any

Solution

This one is a bit trickier than it first appears due to how typescript needs to iterate over arrays to get their values.The idea for this challenge will be to map each index into an objects key, and have the result of true or false as the indexes value.

To iterate over an arrays keys to give a different result type per key, we can use an index signature in an object. For now we can set the value to be a boolean which we will change later.

type Includes<T extends readonly any[], U> = {
  // Will add a property for every index of the T array
  [Key in keyof T]: boolean;
};

/**
 * The result type for ([1,2,3], 2) is:
 *   [boolean, boolean, boolean]
 */

The next step is to replace the boolean type with true or false depending on whether it matches the type of U. We will make use of the given Equal type that is used by the assertions as Equal is surprisingly complex to create in Typescript.

type Includes<T extends readonly any[], U> = {
  // Will add a property for every index of the T array
  [Key in keyof T]: Equal<T[Key], U>;
};

/**
 * The result type for ([1,2,3], 2) is:
 *   [false, true, false]
 */

The last step is to take the type we currently have is a check for any elements equaling true. It turns out that the easiest method is to actually check if all the elements are false. If they are all false then we have no match, but if any are not false then we have a match.

This method is easier as we can do a check on all indexes equaling false through [number] extends false. If we did the same for true all elements would have to match for a true result.

type Includes<T extends readonly any[], U> = {
  [Key in keyof T]: Equal<T[Key], U>;
}[number] extends false ? false : true;

/**
 * The result type for ([1,2,3], 2) is: true
 */


What to read more? Check out more posts below!