Динамические ключи и проверка типов значений в машинописи - PullRequest
0 голосов
/ 01 апреля 2019

Я начал изучать машинопись.Я уверен, что может быть такой же билет, как этот, но я хотел бы быстро взглянуть на это.

i have keys
type keys = 'a' | 'e' | 'i' | 'o' | 'u';
I want these to restrict the possible a keys in an object
{
numbers : number;
symbols : string;
[key : keys] : string | number | boolean;
}

Однако я получаю эту ошибку An index signature parameter type cannot be a union type. Consider using a mapped object type instead., поэтому я попытался

{
numbers : number;
symbols : string;
[key in keys] : string | number | boolean;
}

но я получил another error от TSLint.Я надеюсь, если кто-нибудь может помочь мне с этими примерами, почему и как они меняются?и решение Пожалуйста.

Я хочу получить результат

key with only values of a, e, i, o, u and these Keys can have any of the string, number, boolean types of values.

1 Ответ

0 голосов
/ 01 апреля 2019

Отображенные типы аналогичны индексным сигнатурам , но они не совпадают. Как вы обнаружили, ключи индексных сигнатур могут быть точно string или number. Сопоставленные типы позволяют указывать более узкий набор ключей, но вы не можете добавлять другие свойства к сопоставленному типу.

Что вы можете сделать - это использовать перекресток :

type X = {numbers: number; symbols: string} & {[K in keys]: string | number | boolean}

// type X = {
//  numbers: number;
//  symbols: string;
// } & {
//  a: string | number | boolean;
//  e: string | number | boolean;
//  i: string | number | boolean;
//  o: string | number | boolean;
//  u: string | number | boolean;
// }

Это по сути то же самое, что вы хотите, поскольку пересечение A & B означает, что вы должны соответствовать как A, так и B.

Другим способом представления этого типа является использование сопоставленного условного типа для всего объекта вместо пересечения. Это будет выглядеть сложнее для вас, но для людей будет полезнее:

type Y = { [K in "numbers" | "symbols" | keys]:
  K extends "numbers" ? number :
  K extends "symbols" ? string :
  string | number | boolean };

// type Y = {
// a: string | number | boolean;
// e: string | number | boolean;
// i: string | number | boolean;
// o: string | number | boolean;
// u: string | number | boolean;
// numbers: number;
// symbols: string;

В любом случае должно работать. Надеюсь, это поможет; удачи!

...