【问题标题】:Generic Object type in typescript打字稿中的通用对象类型
【发布时间】:2017-03-31 04:43:15
【问题描述】:

在打字稿中是否有任何方法可以为变量分配通用对象类型。 这就是我所说的“通用对象类型”

let myVariable: GenericObject = 1 // Should throw an error
                              = 'abc' // Should throw an error
                              = {} // OK
                              = {name: 'qwerty'} //OK

即它应该只允许将 javascript 对象分配给变量,而不允许其他类型的数据(数字、字符串、布尔值)

【问题讨论】:

    标签: typescript types


    【解决方案1】:

    有点切线,因为我在其他地方没有找到类似的答案,来自@JaredMcAteer 这里,使用record 帮助我混合枚举+对象。

    enum FOO_ENUM {
      BAR = 'BAZ';
    }
    
    type FOO_OBJECT_TYPE = { ... };
    
    const BIZ_OBJECT: Record<FOO_ENUM, FOO_OBJECT_TYPE> = {
      [FOO_ENUM.BAR]: { ... }
    }
    

    在我输入 BIZ_OBJECT 之前在哪里
    BIZ_OBJECT: {[type: string]: FOO_OBJECT}
    允许BIZ_OBJECT.asd 之类的东西,现在只能使用来自FOO_ENUM 的密钥,例如

    • BIZ_OBJECT.BAZ // { ... }
    • BIZ_OBJECT.asd // Property 'asd' does not exist on type ...
    • BIZ_OBJECT[FOO_ENUM.BAR] // { ... }
    • BIZ_OBJECT[FOO_ENUM.asd] // Property 'asd' does not ...
    • BIZ_OBJECT[FOO_ENUM['asd']] // ! not caught !

    【讨论】:

    • 除此之外,我建议您将类型命名为FooObjectType,将枚举命名为FooEnum。我个人觉得ALL_CAPS 的类型名称太吵了。
    【解决方案2】:

    Typescript 2.1+ 也有utility typeRecord&lt;K, T&gt;,可以用代替自己定义

    const myObj: Record<string, any>;
    

    当我可以给key 起一个有意义的名字时,我喜欢使用最佳答案中描述的风格,但如果它不是很明显或没有必要,Record 是一个不错的选择。

    【讨论】:

      【解决方案3】:

      从 TypeScript 2.2 开始,您可以使用

      let myVariable: object;
      

      编辑:这是一个例子:

      let myVariable: object = { fun: 1 };
      

      【讨论】:

      • 这不起作用例如:const me: object = {}; me.fun = 1 将抛出错误。 Property 'fun' does not exist on type 'object'.
      • 但是你可以这样做let myVariable: object = { fun: 1 };,这是 OP 要求的。
      • 内置的object 类型也没有定义索引签名,所以它不是通用对象的一个​​很好的占位符,很遗憾。
      • @BillBarnes 没有人创建一个对象将其留空,OP 在第 3 行显示一个空对象,因此这不是 OP 所要求的。
      • 不要为此使用object。它存在的原因不同:删除原语:youtube.com/watch?v=0y5hhzuQjCA
      【解决方案4】:

      确定:

      type GenericObject = { [key: string]: any };
      
      let myVariable1: GenericObject = 1; // Type 'number' is not assignable to type '{ [key: string]: any; }'
      let myVariable2: GenericObject = 'abc'; // Type 'string' is not assignable to type '{ [key: string]: any; }'
      let myVariable3: GenericObject = {} // OK
      let myVariable4: GenericObject = {name: 'qwerty'} //OK
      

      (code in playground)

      【讨论】:

      • 至少在 TS 4.1.3 上,当我尝试将其传递给 new Proxy() 时,我收到错误 TS2345: Argument of type 'GenericObject' is not assignable to parameter of type 'object'.。有什么想法吗?
      • @Romasato 当我在 ts 操场(ts 4.1.2)中尝试它时效果很好,你能在那里重现它吗?
      猜你喜欢
      • 2018-09-19
      • 2020-10-11
      • 2021-11-06
      • 2018-09-15
      • 2020-06-10
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多