With the introduction of Variadic Tuple Types in TypeScript 4.0, a new type construct that allows for interesting possibilities such as concantenation functions has been made available. An example from the documentation illustrates this:
type Arr = readonly any[];
function concat<T extends Arr, U extends Arr>(arr1: T, arr2: U): [...T, ...U] {
return [...arr1, ...arr2];
}
This raises the question of whether Variadic Tuple Types can be leveraged to type a function that calculates the Cartesian Product. The goal would be for the function to infer the types of its arguments and produce an appropriate return type. For instance, providing [number[], string[]]
as input should yield a result of type [number, string][]
. While there are various implementations of Cartesian Product functions available, none are strictly typed. One example is shown below:
const cartesian =
(...a) => a.reduce((a, b) => a.flatMap(d => b.map(e => [d, e].flat())));
The current implementation I am using does not make use of Variadic Tuple Types and instead requires explicit type casting as seen here:
const cartesian = <T extends any[]>(...arr: any[][]): T[] =>
arr.reduce<T[]>(
(a, b) => a.flatMap<T>(c => b.map<T>(d => [...c, d] as T)),
[[]] as T
);
const product = cartesian<[number, string]>([1, 2, 3], ['a', 'b', 'c']);
Seeking a solution without relying on explicit type casting, I believe that Variadic Tuple Types could provide a more elegant approach for typing a Cartesian Product function.
Question
How can Variadic Tuple Types be utilized to automatically infer types for a Cartesian Product function?