у меня есть это
Type T = Params<[Tuple1, Tuple2]> // eg [[string], [number]]
Как из него сделать (сплющить)
Type Flatten<T> = Params<[string, number]>
у меня есть это
Type T = Params<[Tuple1, Tuple2]> // eg [[string], [number]]
Как из него сделать (сплющить)
Type Flatten<T> = Params<[string, number]>
Мы можем сделать это с помощью сопоставленных типов. Рассмотрим код:
type T = Params<[Tuple1, Tuple2]>
// utility type
type Flatten<T extends any[]> = {
[K in keyof T]: T[K] extends any[] ? T[K][0] : T[K]
}
type Result = Flatten<T>
// evaluates into [string, number]
const a: Result = ['a', 1] // correct value of the type
Обратите внимание, как работает Flatten
:
[K in keyof T]
- означает, что мы хотим иметь все ключи, поэтому в кортеже скажем, что элементыT[K] extends any[] ? T[K][0] : T[K]
- мы говорим, что если значение элемента в данном ключе является массивом, тогда дайте мне тип первого элемента этого массива (индекс 0), если не оставьте его как есть, так как нечего сглаживатьЕсли ваши кортежи учитывают более одного типа элемента, то приведенное выше решение будет принимать только первый. Таким образом, для кортежа [string, number]
он создаст string
. Если мы хотим собрать все возможные типы внутри кортежа, мы можем создать более сложный тип. Рассмотреть возможность:
type Flatten<T extends any[]> = {
[K in keyof T]: T[K] extends any[] ? T[K][Exclude<keyof T[K], keyof any[]>] : T[K]
}
T[K] extends any[] ? T[K][Exclude<keyof T[K], keyof any[]>] : T[K]
означает, что если наш элемент является массивом, я получаю типы всех элементов, но удаляю типы значений в прототипе массива.В результате Flatten<Params<[string, number]>>
выдаст [string | number]
. Так что все зависит от вашей цели.
Последнее предложение: если вы не рассматриваете другие типы и только вложенные массивы / кортежи, мы можем избежать условных типов. Рассмотрим последнее решение:
type Flatten<T extends E[], E extends any[] = any[]> = {
[K in keyof T]: T[K][Exclude<keyof T[K], keyof any[]>]
}
Вышеупомянутый тип более ограничен, поскольку работает только с [[]]
, но является более кратким и конкретным.
function f(...args: Flatten<T>) {}
- person Maciej Sikora; 18.12.2019
function f(first: Flatten<T>[0], second: Flatten<T>[1]) {}
- person Maciej Sikora; 18.12.2019