【发布时间】:2019-04-26 10:49:00
【问题描述】:
我正在尝试创建可区分联合类型的交集。在尝试了许多不同的方法之后,我发现了 keyof 运算符,它似乎已经工作了。但是,当我将运算符泛化为偏函数时,它不起作用。
class Account { ... }
type ILoggedIn =
| { isLoggedIn: boolean; loggedInUser?: any }
| { isLoggedIn: false; loggedInUser?: undefined }
| { isLoggedIn: true; loggedInUser?: any }
type IInitialized =
| { initialized: boolean; account?: undefined }
| { initialized: false; account?: undefined }
| { initialized: true; account?: Account }
type IContextWorks = { [K in keyof ILoggedIn]?: ILoggedIn[K] } &
{ [K in keyof IInitialized]?: IInitialized[K] }
type Partial<T> = { [P in keyof T]?: T[P] }
type IContextNotWork = Partial<ILoggedIn> & Partial<IInitialized>
const valueWorks: IContextWorks = {
account: new Account(),
initialized: true,
isLoggedIn: true,
loggedInUser: {},
}
const valueNotWork: IContextNotWork = {
account: new Account(),
initialized: true,
isLoggedIn: true,
loggedInUser: {},
}
我使用NotWork版本时遇到的错误是:
Type 'boolean' is not assignable to type 'true | undefined'.
我会假设要么两者都可以工作,要么两者都不能工作,但在这种情况下,只有一个工作。
我做错了什么?
【问题讨论】:
-
什么是
IXyaInitialized?我can't reproduce你的错误。 -
另外,
IContextWorks不再是有区别的联合。歧视工会:{kind: "s", value: string} | {kind: "n", value: number}。不是:{kind: "s" | "n", value: string | number}。特别是像{kind: "s", value: 7}这样的值匹配后一种类型,但不匹配前一种类型。 -
我的理解是您正在尝试创建 9 种交集类型的联合,对吗?
-
您可以为此使用有区别的联合,但实际上,如果您只是在寻找一个属性的存在,您不需要为它存储单独的布尔值,您可以在计算时计算该布尔值需要它...(例如,
typeof value.account !== 'undefined') -
如果您无法在独立环境中重现该问题,那么我想您的下一步是分析您看到错误的环境并尝试找出不同之处。如果错误仅发生在某个版本的 TypeScript 或某些编译器选项中,那么这与问题相关,应该进行编辑。祝你好运!
标签: typescript