简体   繁体   English

Typescript 接口可选属性取决于其他属性

[英]Typescript interface optional properties depending on other property

Let's say we have the following Typescript interface :假设我们有以下 Typescript interface

interface Sample {
    key1: boolean;
    key2?: string;
    key3?: number;
};

In this case, key1 is always required, key2 is always optional, while key3 should exist if key1 is true and should not exist if key1 is false .在这种情况下, key1始终是必需的, key2始终是可选的,而如果key1true ,则 key3 应该存在,如果key1false则不应该存在。 In another word, a key's occurrence depends on another key's value.换句话说,一个键的出现取决于另一个键的值。 How can we achieve this in Typescript?我们如何在 Typescript 中实现这一点?

The most straightforward way to represent this is with a type alias instead of an interface:最直接的表示方法是使用类型别名而不是接口:

type Sample = {
  key1: true,
  key2?: string,
  key3: number
} | {
  key1: false,
  key2?: string,
  key3?: never
}

In this case the type alias is the union of two types you're describing.在这种情况下,类型别名是您所描述的两种类型的联合 So a Sample should be either the first constituent (where key1 is true and key3 is required) or the second constituent (where key1 is false and key3 is absent).因此, Sample应该是第一个成分(其中key1为 true 且需要key3 )或第二个成分(其中key1为 false 且key3不存在)。

Type aliases are similar to interfaces but they are not completely interchangeable.类型别名类似于接口,但它们不能完全互换。 If using a type alias leads to some kind of error, please add more detail about your use case in the question.如果使用类型别名导致某种错误,请在问题中添加有关您的用例的更多详细信息。

Hope that helps.希望有帮助。 Good luck!祝你好运!

Thought I'd mention another nice approach here could be to use a discriminated union:以为我会在这里提到另一种不错的方法是使用受歧视的联合:

enum ShapeKind {
    Circle,
    Square,
}

interface Circle {
    kind: ShapeKind.Circle;
    radius: number;
}

interface Square {
    kind: ShapeKind.Square;
    sideLength: number;
}

let c: Circle = {
    kind: ShapeKind.Square,
    //    ~~~~~~~~~~~~~~~~ Error!
    radius: 100,
}

As described in the Typescript docs: https://www.typescriptlang.org/docs/handbook/enums.html#union-enums-and-enum-member-types如 Typescript 文档中所述: https ://www.typescriptlang.org/docs/handbook/enums.html#union-enums-and-enum-member-types

I think that a readable solution is to use overload我认为一个可读的解决方案是使用重载

so we can do this:所以我们可以这样做:

type IOverload = {
  (param: { arg1: number }): any;
  (param: { arg1: number; arg2: string; arg3: number }): any;
};

const sample: IOverload = (args) => {...};

sample({ arg1: 1, arg2: 'a' });

===> Property 'arg3' is missing in type '{ arg1: number; arg2: string; }' but required 
in type '{ arg1: number; arg2: string; arg3: number; }'.

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Typescript 接口属性希望根据其他属性将可选更改为必需 - Typescript interface property want to change optional to required depending on other property 如何使用TypeScript根据另一个属性将React组件的两个属性设置为可选属性? - How to set two properties for a React component as optional depending on another property using TypeScript? 在Typescript中管理可选接口属性的最佳实践? - Best practices for managing optional interface properties in Typescript? 带有可选属性子集的 TypeScript 通用属性 - Generic Property on TypeScript with subset of optional properties Typescript:获取接口参数时仅命名/解构可选属性? - Typescript: only name/destructure optional properties when taking an interface parameter? TypeScript Interface中的可选功能 - TypeScript Optional function in Interface TypeScript:如何在构造函数中设置对象属性(取决于对象属性) - TypeScript: How to set object property in constructor (depending on object properties) 定义一个Typescript接口,其中属性是现有对象的属性 - Define A Typescript Interface Where A Property Is An Existing Object's Properties 使一个属性的类型取决于其他属性 - Make the type of one property depending upon other properties TypeScript接口可选参数但不视为可选 - TypeScript interface optional parameter but not viewed as optional
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM