Как я могу легко конвертировать из числительных c Перечисления в строку или число и наоборот в Typescript? - PullRequest
0 голосов
/ 20 января 2020

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

enum Direction {
  Up, Down, Left, Right
}

Я хотел бы преобразовать Direction или любой другой Enum в моем коде следующим образом:

  • Enum <-> string
  • Enum <-> number
  • number <-> string

Примеры:

let test = Direction.Left;
enumToString(test); // -> 'Left'
enumToNumber(test); // -> 2
stringToNumber('Left'); // -> 2
stringToEnum('Left'); // -> Direction.Left

1 Ответ

0 голосов
/ 20 января 2020

После некоторой обработки я смог выполнить все запрошенные функции конвертера (с Generics), удовлетворяя компилятору Typescript. Я также добавил stringExists и numberExists, чтобы проверить, существует ли ключ.

Два важных предупреждения: он работает только с цифрами c Перечислениями и Я тестировал его только с помощью Typescript 3.7.5

// For *numeric* Enums !
export class EnumUtils {
  public static numberToString<T>(enumType: T, n: number): string {
    return enumType[n as keyof T] + '';
  }
  public static stringToEnum<T>(enumType: T, s: string): T[keyof T] {
    return enumType[s as keyof T];
  }
  public static enumToNumber<T>(enumType: T, s: T[keyof T]): number {
    return +s; // enumType parameter must not be removed (for type checking)
  }
  public static stringToNumber<T>(enumType: T, s: string): number {
    return EnumUtils.enumToNumber(enumType, EnumUtils.stringToEnum(enumType, s));
  }
  public static numberToEnum<T>(enumType: T, n: number): T[keyof T] {
    return EnumUtils.stringToEnum(enumType, EnumUtils.numberToString(enumType, n));
  }
  public static enumToString<T>(enumType: T, s: T[keyof T]): string {
    return EnumUtils.numberToString(enumType, EnumUtils.enumToNumber(enumType, s));
  }
  public static stringExists<T>(enumType: T, s: string): boolean {
    return s === EnumUtils.enumToString(enumType, EnumUtils.stringToEnum(enumType, s));
  }
  public static numberExists<T>(enumType: T, n: number): boolean {
    return n === EnumUtils.enumToNumber(enumType, EnumUtils.numberToEnum(enumType, n));
  }
}

Как только вы сохраните это в файле 'enum-utils.ts', вот несколько тестов, которые вы можете выполнить:

import { EnumUtils } from './enum-utils.ts';

enum Direction {
  Up, Down, Left, Right
}

const test1: Direction = EnumUtils.stringToEnum(Direction, 'Left');
const test2: string = EnumUtils.enumToString(Direction, Direction.Left);
const test3: Direction = EnumUtils.numberToEnum(Direction, 2);
const test4: number = EnumUtils.enumToNumber(Direction, Direction.Left);
const test5: number = EnumUtils.stringToNumber(Direction, 'Left');
const test6: string = EnumUtils.numberToString(Direction, 2);
const test7: boolean = EnumUtils.stringExists(Direction, 'Left');
const test8: boolean = EnumUtils.stringExists(Direction, 'randomstring');
const test9: boolean = EnumUtils.stringExists(Direction, '2');
const test10: boolean = EnumUtils.numberExists(Direction, 2);
const test11: boolean = EnumUtils.numberExists(Direction, 999);

// true true true true true true true true true true true
console.log(
  test1 === Direction.Left,
  test2 === 'Left',
  test3 === Direction.Left,
  test4 === 2,
  test5 === 2,
  test6 === 'Left',
  test7 === true,
  test8 === false,
  test9 === false,
  test10 === true,
  test11 === false
);
...