With type ``CountElementNumberToObject``, get the number of occurrences of every item from an array and return them in an object. For example: Master advanced TypeScript type manipulation in this medium-level challenge on TypeScriptPro.
In this medium-level challenge, you'll implement CountElementNumberToObject<T> which counts the occurrences of every element in a potentially nested array and returns an object mapping each element to its count.
With type CountElementNumberToObject, get the number of occurrences of every item from an array and return them in an object. For example:
type Simple1 = CountElementNumberToObject<[]> // return {}
type Simple2 = CountElementNumberToObject<[1,2,3,4,5]>
// return {
// 1: 1,
// 2: 1,
// 3: 1,
// 4: 1,
// 5: 1
// }
type Simple3 = CountElementNumberToObject<[1,2,3,4,5,[1,2,3]]>
// return {
// 1: 2,
// 2: 2,
// 3: 2,
// 4: 1,
// 5: 1
// }Change the following code to make the test cases pass (no type check errors).
type Flatten<T extends any[]> = T extends [infer First, ...infer Rest]
? First extends any[]
? [...Flatten<First>, ...Flatten<Rest>]
: [First, ...Flatten<Rest>]
: []
type FilterNever<T extends any[]> = T extends [infer First, ...infer Rest]
? [First] extends [never]
? FilterNever<Rest>
: [First, ...FilterNever<Rest>]
: []
type Count<T extends any[], V, Acc extends unknown[] = []> = T extends [infer First, ...infer Rest]
? Equal<First, V> extends true
? Count<Rest, V, [...Acc, unknown]>
: Count<Rest, V, Acc>
: Acc['length']
type CountElementNumberToObject<T extends any[], F extends any[] = FilterNever<Flatten<T>>> = {
[K in F[number] as K & PropertyKey]: Count<F, K>
}How it works:
Flatten<T> recursively flattens nested arrays into a single-level tuple, so [1, [2, [3]]] becomes [1, 2, 3]FilterNever<T> removes any never values from the flattened array, since [never] should produce an empty object {}Count<T, V> counts how many times value V appears in the array by using an accumulator tuple Acc and returning its lengthCountElementNumberToObject combines everything: it flattens, filters never, then maps over each unique element using F[number] as the key (cast to PropertyKey) with its count as the valueK & PropertyKey intersection ensures only valid property keys (strings, numbers, symbols) are used as object keysThis challenge helps you understand deep array flattening, element counting at the type level, and mapped types with key remapping, and how to apply these concepts in real-world scenarios.
This challenge is originally from here.
Be the first to access the course, unlock exclusive launch bonuses, and get special early-bird pricing before anyone else.
Only 27 Spots left
Get 1 month early access
Pre-Launch discount