Question
What is the point of inferring a type in a conditional type only to return the inferred type?
I have been looking at this post as well as this monster of an answer to another post, which has piqued my curiosity for understanding conditional types, distributive conditional types, and the infer keyword.
I have reviewed the following posts related to the infer
keyword:
- Why is the infer keyword needed in Typescript?
- TypeScript: What is the context of P in `T extends infer P`? (unclear where `P` come from)
- Trying to understand the limits of 'T extends infer U'
At this point, my understanding is that:
- Conditional types are used when you would like to flexibly change the expected return type given some criteria. For example, if a variable extends
number
then return1
otherwise return'string'
. infer
is used to tell the compiler "take your best guess as to what this variable's type should be"
Why and when is it useful (or necessary) to write something like the following?:
type GenericType<T> = T extends infer R ? R : never;
I'm assuming that it is useful / necessary (and not just used for illustrative purposes) based on the 3 previous posts I've linked.
I can understand that this essentially tells the compiler "Confirm that the generic type T conforms to the type R. If that is true, then return R. Otherwise return never"
. However, since R
is inferred from T
and R
is within the conditional type's scope, is it ever any different from T
? Wouldn't the condition always evaluate to true
?
In practice, I don't see any functional difference between these type definitions (playground):
type GenericType1<T> = T extends infer R ? R : never;
type GenericType2<T> = T extends T ? T : never;
type GenericType3<T> = T;
type FooBar = {a: 'foo', b: 'bar'};
const Example1: GenericType1<FooBar> = {a: 'foo', b: 'bar'};
const Example2: GenericType2<FooBar> = {a: 'foo', b: 'bar'};
const Example3: GenericType3<FooBar> = {a: 'foo', b: 'bar'};
const Example4: FooBar = {a: 'foo', b: 'bar'};