我读过Operator '==' cannot be applied to types x and y in Typescript 2这篇文章,但对我的案例没有什么帮助。
在TypeScript2.5.3中,我们使用以下形式的字符串枚举来定义许多模型:

export interface Event {
   category: "MORNING" | "NIGHT";
   enabled: boolean;
}

然后对它们应用比较器,如:
morning = events.filter(event => event.category === 'MORNING');

毫无怨言。
现在,在这个代码片段中:
if (event.enabled || event.category === 'MORNING') {
 // something
}
else if (event.category !== 'MORNING') {
 // something else
}

我在Operator '!==' cannot be applied to types '"MORNING"' and '"NIGHT"'条件中得到了else if编译错误,但在if条件下没有使用相同的(但相反的)比较器。
进一步减少示例,将编译以下代码:
if (event.category !== 'MORNING') {
 // something
}
else if (event.category !== 'MORNING') {
 // something else
}

它汇编了:
if (event.category !== 'MORNING') {
 // something
}
else if (event.category === 'MORNING') {
 // something else
}

但这会抛出一个错误(在else if行中):
if (event.category === 'MORNING') {
 // something
}
else if (event.category !== 'MORNING') {
 // something else
}

我误解了类型检查器的哪些基本属性?
(注意:最后的示例是从更复杂的情况中减少的,因此我不能使用简单的else

最佳答案

您得到一个错误,因为编译器已经知道在else if条件点,event.category不是'MORNING'并且不再允许您将event.category与它进行比较。
如果此条件计算为false

if (event.enabled || event.category === 'MORNING') {
 // something
}

那么根据定义,event.category不是'MORNING',因此是'NIGHT'。编译器不允许您再次将其与'MORNING'进行比较(而且确实没有必要再次将其与'MORNING'进行比较),因为在计算'MORNING'条件时,已经知道它不是else if
顺便说一句,以下代码产生编译错误的原因基本相同:
if (event.category !== 'MORNING') {
 // something
}
else if (event.category !== 'NIGHT') {
 // something else
}

同样地:
if (event.category === 'MORNING' || event.category !== 'MORNING') {
 // something
}

这是由于typescript在计算后续布尔表达式时“缩小”联合类型的方式造成的。
如以下评论所示,请参见https://www.typescriptlang.org/docs/handbook/release-notes/typescript-2-0.html#control-flow-based-type-analysis,也请参见https://github.com/Microsoft/TypeScript/blob/master/doc/spec.md#4.24

10-04 22:33