Gebruik Enum als beperkt sleuteltype in Typescript

De vraag is of enum kan worden gebruikt als een sleuteltype in plaats van alleen “nummer” of “tekenreeks”? Momenteel lijkt het erop dat de enige mogelijke declaratie x:{[key:number]:any} is, waarbij de sleutel van het type “number” of “string” kan zijn. Is het mogelijk om zoiets te maken als in dit voorbeeld:

Voorbeeld:

enum MyEnum
{
    First,
    Second
}
var layer:{[key:MyEnum]:any};

Antwoord 1, autoriteit 100%

Sinds 2018is er een eenvoudigere manier in Typescript, zonder gebruik van keyof typeof:

let layer: { [key in MyEnum]: any}

Om niet alle sleutels op te hoeven nemen:

let layer: { [key in MyEnum]?: any}

Antwoord 2, autoriteit 98%

Ja. Typ gewoon

let layer:{[key in keyof typeof MyEnum]: any}

Het keyoftrefwoord is beschikbaar sinds Typescript 2.1. Zie de TypeScript-documentatievoor meer details.
Alleen keyofgebruiken voor enums zou niet werken (je zou de sleutels van het type enumkrijgen en niet de enum-constanten), dus je moet keyof typeof.


Antwoord 3, autoriteit 63%

Kort antwoord:

let layer: Partial<Record<MyEnum, unknown>>;

Lang antwoord (met details):

Ik had hetzelfde probleem. Ik wilde het volgende stukje code laten werken.

enum MyEnum {
    xxx = "xxx",
    yyy = "yyy",
    zzz = "zzz",
}
type myType = ...; // Fill here
const o: myType = { // keys should be in MyEnum, values: number
   [MyEnum.xxx]: 2,
   "hi": 5, // <--- Error: complain on this one, as "hi" is not in enum
}
o[MyEnum.yyy] = 8; // Allow it to be modified later

Uitgaande van het andere antwoordop deze vraag, moet ik:

type myType = {[key in keyof typeof MyEnum]: number};

Maar het zou zeuren dat o is missing "yyy". Dus ik moest zeggen dat het object sommigevan de enum-sleutels zal hebben, niet allemaal. Dus ik moet ?toevoegen om:

type myType = {[key in keyof typeof MyEnum]?: number};

Het werkte prima, totdat ik de regel aan het einde van de code toevoegde om het object te wijzigen nadat het voor het eerst was gemaakt. Nu klaagde het dat het type geërfd via keyofzijn eigenschappen heeft als readonlyen ik kan ze niet aanraken na de eerste creatie! 😐 Als u de muisaanwijzer op myTypein Typescript Playgroundhoudt, wordt het weergegeven als :

type myType = {
    readonly xxx?: number | undefined;
    readonly yyy?: number | undefined;
    readonly zzz?: number | undefined;
}

Om die ongewenste readonlyte verwijderen, ontdekte ik dat ik het volgende kan gebruiken:

type myType = { -readonly [key in keyof typeof myEnum1]?: number };

Heel lelijk, maar het werkt!

Totdat ik met Typescript hulpprogramma’sspeelde, en gevonden wat ik wilde!

type myType = Partial<Record<MyEnum, number>>;

🙂


Antwoord 4, autoriteit 13%

Voor degenen die op zoek zijn naar een manier om de keysvan de enumte krijgen in plaats van de value, hoeft u hier alleen maar vanaf te veranderen :

type myType = Partial<Record<MyEnum, number>>;

daarop:

type myType = Partial<Record<keyof typeof MyEnum, number>>;

Antwoord 5, autoriteit 4%

eigenlijk werkte het bij mij zonder enige oplossing.

hier zijn enkele gevallen:

enum EnumString {
  a="a",
  b="b"
}
enum EnumNum {
  a,
  b
}
type Type = "a" | "b"
let x1:{[k in EnumString]?:any }={a:1} //working
let x2:{[k in EnumNum]?:any }={a:1} //error: Type '{ a: number; }' is not assignable to type '{ 0?: any; 1?: any; }'
let x3:{[k in Type]?:any }={a:1} //working; defining a union type is easer than defining an enum string 
let y1:{[k: EnumString]?:any }={a:1}
let y2:{[k: EnumNum]?:any }={a:1}
let y3:{[k in Type]?:any }={a:1}
let z1:{[k in keyof typeof EnumString]?:any }={a:1}
let z2:{[k in keyof typeof EnumNum]?:any }={a:1}
let z3:{[k: keyof typeof Type]?:any }={a:1}

het is belangrijk op te merken dat de case “z1”, zelfs het werkt goed, maar je kunt het later niet wijzigen omdat het een alleen-lezen is. u kunt het trefwoord -readonlygebruiken om deze beperking op te heffen.

x1.a=2 
x3.a=2
z1.a=2 //error: read only

Ik heb een typoscript speeltuinom zelf problemen met verschillende gevallen te bekijken

Other episodes