【问题标题】:Initialize empty object in typescript with Record type使用 Record 类型初始化打字稿中的空对象
【发布时间】:2021-01-21 19:13:24
【问题描述】:

如何定义和初始化一个可以为空的对象。

有类型

type Plan = 'plan1' | 'plan1';

interface IPlan {
    name: string
}

当我尝试初始化一个空对象时,我收到了一个错误

const plans: Record<Plan, Readonly<IPlan> = {}; // **ERROR HERE**

plans.plan1 = {
    name: 'Plan #1'
}

类型“{}”中缺少属性“plan1”,但类型“Record' 中是必需的。

Playgro

【问题讨论】:

  • 您的完整用例是什么?空对象{} 不是Record&lt;Plan, Readonly&lt;IPlan&gt; 类型。你为什么不去const plan1 = { name: "Plan #1" } 然后const plans = { plan1 }?换种方式问:为什么要初始化empty,然后手动填充,而不是最后直接声明你想要的完整的plans对象?

标签: typescript typescript-typings


【解决方案1】:

只需使用 Partial 实用程序类型:Partial&lt;Type&gt;

type Plan = 'plan1' | 'plan1';

interface IPlan {
    name: string
}


const plans: Partial<Record<Plan, IPlan>> = {}; // no error

plans.plan1 = {
    name: 'Plan #1'
}

这种方法的缺点是现在界面的所有属性都是可选的。但是由于您希望它在没有所需属性的情况下实例化,所以这是唯一的方法。

Playground Link

另一个想法可能是使用 Omit 实用程序类型:Omit&lt;Type, Keys&gt;

interface Plan {
  name: string;
}

type IPlan = Omit<Plan , "name">;

const plans: IPlan = {};

因此,同样,您可以在没有所需属性的情况下进行实例化。

Playground Link

【讨论】:

    【解决方案2】:

    你可以这样做:

    type Plan = 'plan1' | 'plan2';
    
    interface IPlan {
        name: string
    }
    
    type PlansRecord = Record<Plan, Readonly<IPlan>>
    const plansRecord = {} as PlansRecord
    
    console.log({plansRecord})
    

    输出: [LOG]: { "plansRecord": {} }

    Demo

    【讨论】:

    • 我不确定这是否是个好主意。至少它应该只在本地使用(例如在构建这样一个对象然后返回它的函数中)。否则,如果您将 plansRecord 传递给代码库的其他部分,您将无法信任这些类型,并且可能会遇到意外错误。
    【解决方案3】:

    查看 the documentation 的 Typescript 的 Record,看起来他们需要更精细的对象定义:

    const plans: Record<Plan, Readonly<IPlan>> = {plan1: {name: 'foo'}, plan2: {name:'bar'}}
    

    或:

      const plans: Record<Plan, Readonly<IPlan>> = {plan1: {name: 'foo'}}
    

    如果您只是想创建一个带有类型的元素,您可以只使用带有可选属性 (see here) 的类或接口。例如:

    interface IPlan {
        name?: string;
    }
    

    【讨论】:

    • 这正是我需要的......更精致的对象。定义为具有plan1 或plan2 属性的对象或空对象{} like...{ plan1: {name: 1} }{ plan1: {name: 'foo'}, plan2: {name: 'bar'} } 甚至{}
    猜你喜欢
    • 1970-01-01
    • 2020-07-26
    • 2021-07-24
    • 2018-08-14
    • 1970-01-01
    • 2021-08-15
    • 1970-01-01
    • 1970-01-01
    • 2017-09-06
    相关资源
    最近更新 更多