📖 Scenario: You are working on a TypeScript project where you want to extract the type of elements inside an array type automatically. This helps you avoid repeating types and makes your code cleaner.
🎯 Goal: Build a TypeScript utility type called ElementType that uses the infer keyword to extract the type of elements inside an array type.
📋 What You'll Learn
Create a generic type called ElementType that takes one type parameter T.
Use a conditional type with infer to extract the element type from an array type.
Test the ElementType type with an example array type.
Print the inferred element type using a type alias and a variable.
💡 Why This Matters
🌍 Real World
In real projects, you often work with complex types like arrays or functions. Using <code>infer</code> helps you automatically get inner types without repeating them.
💼 Career
Understanding <code>infer</code> is important for advanced TypeScript programming, useful in building libraries, frameworks, or large applications with strong type safety.
Progress0 / 4 steps
1
Create an example array type
Create a type alias called MyArray that is an array of number.
Typescript
Hint
Use type MyArray = number[]; to define an array of numbers.
2
Create the ElementType generic type with infer
Create a generic type alias called ElementType with one type parameter T. Use a conditional type with T extends (infer U)[] to infer the element type U. Return U if T is an array type, otherwise return never.
Typescript
Hint
Use infer U inside the conditional type to extract the element type.
3
Test the ElementType type with MyArray
Create a type alias called Test that uses ElementType with MyArray as the type argument.
Typescript
Hint
Use type Test = ElementType; to test the inferred type.
4
Print the inferred type using a variable
Create a constant variable called value with type Test and assign it the number 42. Then, print value using console.log.
Typescript
Hint
Use const value: Test = 42; and console.log(value); to show the inferred type works.
Practice
(1/5)
1. What does the infer keyword do in TypeScript conditional types?
easy
A. It declares a new variable inside a function.
B. It allows TypeScript to guess and extract a type inside a conditional type.
C. It creates a new interface automatically.
D. It imports types from external modules.
Solution
Step 1: Understand the role of infer
The infer keyword is used inside conditional types to let TypeScript guess a type variable from a given type.
Step 2: Identify what infer extracts
It extracts parts of complex types, like the return type of a function or the element type of an array.
Final Answer:
It allows TypeScript to guess and extract a type inside a conditional type. -> Option B
2. Which of the following is the correct syntax to infer the return type of a function type F using infer?
easy
A. type ReturnType<F> = F extends (...args: any[]) => infer R ? R : never;
B. type ReturnType<F> = infer R extends F ? R : never;
C. type ReturnType<F> = F extends infer R => any ? R : never;
D. type ReturnType<F> = F extends (...args: infer R) => any ? R : never;
Solution
Step 1: Analyze the conditional type structure
The correct syntax uses F extends (...args: any[]) => infer R to extract the return type R.
Step 2: Check each option for correct infer usage
type ReturnType<F> = F extends (...args: any[]) => infer R ? R : never; correctly places infer R after the arrow function parameters and before the return type.
Final Answer:
type ReturnType<F> = F extends (...args: any[]) => infer R ? R : never; -> Option A
Quick Check:
Correct infer syntax for return type = A [OK]
Hint: Look for infer R right after function args in extends [OK]
Common Mistakes:
Placing infer outside the extends clause
Using infer on the wrong part of the function type
Confusing parameter inference with return type inference
3. Given the following code, what is the type of ElementType?
type ElementType<T> = T extends (infer U)[] ? U : T;
type Result = ElementType;
medium
A. string
B. unknown
C. never
D. string[]
Solution
Step 1: Understand the conditional type with infer
The type checks if T extends an array of some type U. If yes, it extracts U.
Step 2: Apply the type to string[]
Since string[] extends (infer U)[], U is string. So, ElementType<string[]> is string.
Final Answer:
string -> Option A
Quick Check:
Extracted element type = string [OK]
Hint: infer extracts array element type inside conditional [OK]
Common Mistakes:
Confusing the whole array type with element type
Assuming infer returns the original type
Ignoring the conditional fallback
4. Identify the error in this type definition that tries to infer the argument type of a function:
type ArgType<T> = T extends (arg: infer A) => void ? A : never;
type Test = ArgType<() => number>;
medium
A. The conditional type should check for return type, not argument type.
B. The syntax of infer is incorrect; it should be outside the parentheses.
C. The function type has no arguments, so infer fails and returns never.
D. The type alias is missing a generic constraint.
Solution
Step 1: Analyze the function type used
The function type () => number has no arguments.
Step 2: Understand infer behavior with no matching argument
The conditional type tries to infer argument A, but since there is no argument, the condition fails and returns never.
Final Answer:
The function type has no arguments, so infer fails and returns never. -> Option C
Quick Check:
Infer fails with no matching argument = C [OK]
Hint: Check if function actually has arguments before inferring [OK]
Common Mistakes:
Assuming infer always succeeds
Misplacing infer keyword syntax
Confusing argument and return type inference
5. You want to create a type Flatten<T> that extracts the element type from nested arrays using infer. For example, Flatten<number[][]> should be number[]. Which of the following correctly implements this?
hard
A. type Flatten<T> = T extends (infer U)[] ? U[] : T;
B. type Flatten<T> = T extends (infer U)[] ? Flatten : T;
C. type Flatten<T> = T extends any[] ? Flatten : T;
D. type Flatten<T> = T extends (infer U)[] ? U extends any[] ? Flatten<U> : U[] : T;
Solution
Step 1: Understand the goal of Flatten
We want to recursively unwrap nested arrays until we reach a non-array element, then wrap it back as a single array.
Step 2: Analyze type Flatten<T> = T extends (infer U)[] ? U extends any[] ? Flatten<U> : U[] : T;'s recursive conditional
type Flatten<T> = T extends (infer U)[] ? U extends any[] ? Flatten<U> : U[] : T; checks if T is an array of U. If U is itself an array, it recursively calls Flatten<U>. Otherwise, it returns U[]. This matches the requirement.
Final Answer:
type Flatten<T> = T extends (infer U)[] ? U extends any[] ? Flatten<U> : U[] : T; -> Option D
Quick Check:
Recursive infer for nested arrays = B [OK]
Hint: Use recursive conditional with infer to unwrap nested arrays [OK]
Common Mistakes:
Not handling recursion for nested arrays
Returning wrong type shape after unwrapping
Misplacing infer or conditional checks
Recommended
Ready to prove it?
Pass the test and this pattern moves unknownstrongwhile earning +1 Grip toward your certificate.