Alexander Nechay Alexander Nechay - 2 months ago 11
TypeScript Question

Why TypeScript can not infer type of recursive function

I have the following example code:

//Derived type of sum ([head, ...tail]: number[]) => any
let sum =
([head, ...tail]: number[]) => head ? head + sum(tail) : 0
let x: string = sum([1, 2, 3]);

Why TypeScript infers return type of
to be
? Flow reports an error for this code which, I believe, is correct.


There's an issue (Recursive functions are inferred to have return type any) about this from June 2nd 2015, and it was closed as "by design" saying:

We briefly had a spec that outlined how this could all work in theory, but it didn't make it to implementation.
The current rule is that any function that sees itself during the resolution of its return type is any. This seems to be good enough in practice, since it's always possible to add the needed type annotation and most functions aren't recursive like this due to tail call optimizations not being part of the ES spec yet

So basically, just declare the return type:

let sum =
  ([head, ...tail]: number[]): number => head ? head + sum(tail) : 0

let x: string = sum([1, 2, 3]); // Error: Type 'number' is not assignable to type 'string'

(code in playground)