【问题标题】:Extract scalar fields only from an interface in typescript仅从打字稿中的接口中提取标量字段
【发布时间】:2021-07-04 18:55:25
【问题描述】:

我有以下界面可用。

interface User {
  id: string
  name: string
  age: number
  gender: Gender
  hobbies: Hobby[]
  addresses: Address[]
}

现在我想要一个包含所有 标量 字段的新类型:

interface UserScalars {
  id: string
  name: string
  age: number
  gender: Gender
}

我知道我可以在这里使用Omit/Exclude,但在我的情况下有很多 scalar 以及 no-scalars 所以Omit/Exclude 只会使我的代码更丑。

这在打字稿中可行吗?

【问题讨论】:

  • 在为 type Scalar = string | number | Gender; 之类的标量创建类型之后,Extract 就是您想要的 type UserScalars = Extract<User, Scalar>;Omit 是您想要的 type UserNonScalars = Omit<User, Scalar>;。您如何让 TypeScript 知道什么是标量和非标量而不至少定义一个(我建议定义 Scalar,因为它的成员比 NonScalar 更不同)。
  • 这是我所做的,但由于某种原因,最终类型,即UserScalarsnever 类型。 typescript type Scalars = string | number \n type UserScalars = Extract<CampaignDbObject, Scalars> \n let x: UserScalars
  • 啊,对不起,你想要的不是Extract(这会从union中提取类型)或Omit(这会省略keys来自类型的属性)。你会想做类似下面回答的PickByValueType
  • 无论如何,非常感谢先生。

标签: typescript interface


【解决方案1】:

是的。有可能:

interface User {
  id: string
  name: string
  age: number
  gender: Gender
  hobbies: Hobby[]
  addresses: Address[]
}

type PickByValueType<T, U> = {
  [K in keyof T as T[K] extends U ? K : never]: T[K]
}

type UserScalars = PickByValueType<User, string | number>;

TS Playground

【讨论】:

  • 哇,它似乎有效,但你能否告诉我如何在一个地方定义所有标量并使用它来代替string | number,我对打字稿很陌生。跨度>
  • @SuhailibnNisar 将标量定义为一种类型,例如type Scalar = string | number;
  • 啊,是的,非常感谢先生,我新注册了堆栈溢出,所以很抱歉我不能为你的答案投票。
  • 当然。你在这里typescriptlang.org/play?#code/…
  • 你可以分享一些资源,我可以在哪里学习这些高级打字稿的东西,我什至不知道用什么关键字来搜索它们。我在说这个:type PickByValueType&lt;T, U&gt; = { [K in keyof T as T[K] extends U ? K : never]: T[K] }
猜你喜欢
  • 2017-10-27
  • 2019-04-23
  • 2019-01-06
  • 1970-01-01
  • 2017-09-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多