-
Notifications
You must be signed in to change notification settings - Fork 13k
Description
Search Terms
lambda, closure, inferring, implicit polymorphism, deduce, type
Suggestion
Even in non-Hindley–Milner type systems like Rust and C++ (c++14 or later) polymorphic lambdas are supported:
C++14:
auto sum = [](auto a, auto b) {
return a + b;
};
sum(1, 2);
Rust:
let sum = |a, b| a + b;
sum(1, 2);
So my suggestion start support this for TyteScript as well:
const sum = (a, b) => a + b; // no errors with noImplicitAny
const num = sum(1, 2);
// `num` infer as number
// `sum` infer as:
// `(a: number, b: number): number => a + b`
const str = sum('a', 'b');
// `str` infer as string
// `sum` type signature updated to:
// `(a: number | string, b: number | string): number | string => a + b`
Note (a: number | string, b: number | string): number | string
is ambiguous and may allow sum(1, 'a')
or sum(1, 'b')
as well so perhaps better always infer lambda as generic with single type parameter:
const sum = <T extends string | number>(a: T, b: T): T => a + b
and fallback to specialisation when a
and b
have different types. Or probably restrict parametric as single uniform type.
Why this necessary?
First of all it's reduce verbosity. But explicit generic lambdas have a lot of problems. For example this:
const sum = <T>(a: T, b: T) => a + b;
const sum = <T extends string | number>(a: T, b: T) => a + b;
Cause to parsing problems with JSX mode.
Also it produce error "Operator '+' cannot be applied to types 'T' and 'T'." even with constrain.
Checklist
My suggestion meets these guidelines:
- This wouldn't be a breaking change in existing TypeScript/JavaScript code
- This wouldn't change the runtime behavior of existing JavaScript code
- This could be implemented without emitting different JS based on the types of the expressions
- This isn't a runtime feature (e.g. library functionality, non-ECMAScript syntax with JavaScript output, etc.)
- This feature would agree with the rest of TypeScript's Design Goals.