如何在打字稿中使用枚举作为索引键类型?

iro*_*nic 16 indexing enums dictionary typescript

考虑以下示例.

enum DialogType {
    Options,
    Help
}

class Dialog { 
    test() : string {
        return "";
    }
}

class Greeter {

    openDialogs: { [key in DialogType]: Dialog | undefined } = {
        0: undefined,
        1: undefined
    };

    getDialog(t: DialogType) {
        return this.openDialogs[t];
    }
}

const greeter = new Greeter();
const d = greeter.getDialog(DialogType.Help);
if (d) document.write(d.test());
Run Code Online (Sandbox Code Playgroud)

也在操场上

它有3个问题/问题:

  1. 为什么我不能在初始化文字中省略属性,即使我将属性声明为'| 未定义"
  2. 为什么我不能使用'DialogType.Options'作为类型键,而必须使用硬编码?
  3. 为什么我必须使用'key in DialogType'而不是'key:DialogType'?(或者我可以吗?)

Tit*_*mir 31

  1. |undefined不会使属性可选,只是意味着它可以undefined,有一个建议使|undefined成员可选,但目前它没有实现.您需要使用?after ]来使所有属性可选

    { [key in DialogType]?: Dialog }
    
    Run Code Online (Sandbox Code Playgroud)
  2. 您可以使用对话框枚举值作为键,但它们需要是计算属性:

    let openDialogs: { [key in DialogType]?: Dialog } = {
        [DialogType.Options]: undefined,
    };
    
    Run Code Online (Sandbox Code Playgroud)
  3. { [key: number or string]: Dialog }是一个索引签名.索引签名仅限于numberstring作为密钥类型(即使两者的联合也不起作用).因此,如果您使用索引签名,则可以按任意numberstring(我们不能仅限于DialogType键)进行索引.您在此处使用的概念称为映射类型.映射类型基本上基于键的并集(在这种情况下是DialogType枚举的成员)和一组映射规则生成新类型.我们上面创建的类型基本上等同于:

    let o: { [DialogType.Help]?: Dialog; [DialogType.Options]?: Dialog; }
    
    Run Code Online (Sandbox Code Playgroud)

  • 那太棒了,非常感谢!我确信“T?” 相当于 'T | undefined',尤其是在看到这个之后:https://www.typescriptlang.org/docs/handbook/advanced-types.html#optional-parameters-and-properties。那么可选类型是等价于某物还是它本身就是一种东西? (3认同)
  • “key in”最终成为我缺少的_key_部分。;) 谢谢! (3认同)
  • @ironic它是一种方式,但不是另一种方式,“T?”类型的属性将被视为“T | undefined”进行空检查,但“T | undefined”类型的属性不会被视为可选 (2认同)