【问题标题】:How to merge an interface and default values of a variable?如何合并接口和变量的默认值?
【发布时间】:2021-12-30 13:10:46
【问题描述】:

我有下面令人作呕的代码,我想将 TypeScript 键入的安全性和变量的默认值结合起来:

interface Store {
  infinoteToken: string | null,
  allNotes: Note[],
  // plenty more
}

export const store: Store = reactive({
  infinoteToken: null,
  allNotes: [],
  // plenty more
})

我最终得到两个带有重复信息的代码块。

有没有办法结合这两个元素来声明一个具有默认值和成员类型的对象?

【问题讨论】:

  • 这里有什么“恶心”? Store 接口保存类型信息,store 变量保存默认值,并且使用store: Store 正确键入。就我而言,没有重复的信息。
  • @DimaParzhitsky: 每当我想更新 store 时,我还必须使用相同的名称更新 Store - 我更愿意只保留一个元素实例(并且都输入并在一个地方初始化)

标签: typescript javascript-objects default-value typing


【解决方案1】:

这一切都可以移动到具有默认实现的类中:

class Store {
  infinoteToken: string | null = null;
  allNotes: Note[] = [];
  // plenty more

}

export const store = reactive(new Store());

【讨论】:

    【解决方案2】:

    您可以声明您的默认对象,然后从中派生类型:

    const STORE_DEFAULTS = {
      infinoteToken: null as string | null,
      allNotes: [] as Note[],
      numericProperty: 1,
      booleanProperty: true,
      // plenty more
    }
    
    interface OptionalStoreProperties {
      optionalString?: string;
      // potentially more
    }
    
    type Store = typeof STORE_DEFAULTS & OptionalStoreProperties ;
    

    Playground Link

    • numericPropertybooleanProperty 等与默认值类型匹配的简单属性将被正确推断。
    • 如果类型与分配的值不同,则必须使用a type assertion 覆盖类型:infinoteToken 可以是null 或字符串,因此as string | null 确保字符串仍然可以分配给它.
    • 空数组也总是需要类型断言。否则allNoteswill default to never[]
    • 如果存在不应初始化的可选属性,则需要将它们添加到类型中。 A type intersection (&)(链接指向旧版 TypeScript Hanbook,因为新版不包含交叉点的说明。旧信息仍然相关)将结合两种类型的属性。

    话虽如此,我建议将类型和默认值分开。它可能看起来像重复的代码,但实际上并非如此。

    1. 更清楚通过仅查看该信息来理解类型,而不是必须在精神上区分哪个属性属于哪个类型(假设隐式分配。
    2. 当它们与所有其他代码分开时,默认值也是更清楚
    3. 如果您添加有关不同事物的 cmets,则您所指的内容会更清楚。也许您想说为什么选择了给定的默认值。或者,也许您想解释如何使用属性。这些不必在同一个地方。
    4. 您还可以有多个默认值。也许不适用于这种类型,但绝对可以根据某些条件决定默认值并仅应用那些。将类型和默认值集分开使此选项保持打开状态,并且更易于扩展。

    【讨论】:

      猜你喜欢
      • 2019-09-21
      • 2012-01-30
      • 2021-02-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-08-27
      • 2016-05-06
      • 1970-01-01
      相关资源
      最近更新 更多