Angular 如何正确处理具有多种类型的TypeScript值

Angular 如何正确处理具有多种类型的TypeScript值,angular,typescript,Angular,Typescript,我有以下TS接口 export interface Item { product: string | Product; } 当我想通过一系列的物品来识字时,我必须消除这种类型。换句话说 items = Items[]; items.forEach(item => { item.product._id }) 将不起作用,因为属性不可应用于字符串。因此,我必须预先检查类型,即: items = Items[]; items.forEach(item => { if (ty

我有以下TS接口

export interface Item {
  product: string | Product;
}
当我想通过一系列的物品来识字时,我必须消除这种类型。换句话说

items = Items[];
items.forEach(item => {
  item.product._id
})
将不起作用,因为属性不可应用于字符串。因此,我必须预先检查类型,即:

items = Items[];
items.forEach(item => {
  if (typeof item.product === 'object') item.product._id
})

我真的不喜欢它的样子。您如何处理这种情况?

Javascript不键入变量,所以我认为您的问题只与IDE有关

第一个也是最明显的解决方案是将变量声明为
any
。没有进一步的问题,但你不会有自动完成

第二种不实用的解决方案是创建类型化变量:

if (item instanceof Product) {
  _item: Product = item;
  // Now you have autocomplete on _item
} else if (typeof item === 'string') {
  _item: string = item;
  // Same here. 
}

这是不实际的,因为您必须编写两次逻辑:一次用于产品,一次用于字符串。但是这可能不实用,但它是详尽的,因为您必须实现这两种逻辑(它们肯定不同,因为您没有将字符串视为对象,反之亦然)

应配备类型防护装置,以缩小类型:

if (item.product && typeof item.product === 'object') item.product._id
或:

如果界面显示
item.product
可能是字符串,则需要进行此检查

否则,应断言类型:

items.forEach(item => {
  (item.product as Product)._id
})

这听起来可能有点奇怪,但第一个/最好的方法应该是“不要使用混合类型字符串| product的类变量”

您的具体用例是什么?为什么有些产品是字符串,有些是类?是否也可以为string类创建一个实例

如果由于某些原因,这不可能实现,您可以使用instanceof检查正确的类型(不要使用typeof=='object',因为这不是真正安全的)


视情况而定;现在还不清楚你想要实现什么,因为你展示的例子没有任何作用。但是你可以使用类型保护,例如,@jornsharpe-itus已经回答了我的问题。将使用类型断言(如您所提到的)。在我的例子中,这是最清晰的解决方案。请注意,只有当所有
s'
产品
属性都是
产品
s,而不是
字符串
s,在这种情况下,允许它出现在原始类型中似乎毫无意义。这是显而易见的。拥有多个类型的最初原因是为了检查类型并避免错误。将在将来从根本上简化调试。不过,谢谢你指出它超越了一种类型-我喜欢它。。。感谢you@Timothy主张,而不是铸造。如果其中一个是
product
s,那么在运行时它实际上是一个字符串,代码就会中断(这是编译器告诉您的开始)。我之所以使用它,是因为这个值实际上可能是字符串或对象。取决于MongoDB ObjectID是否已填充引用对象。在一些回调中,它是有一些不是。问题是,为什么不能将字符串值表示为产品实例?如果Product的字段仅为name&id,我认为更好的方法是将id的类型设置为number | null,并始终创建Product instancesNo its not。。我非常简化了这种情况。产品对象是巨大的。不过,谢谢你的回答。K不过,也许你的具体用例在这里描述起来很复杂,我看不出你的产品是一个字符串还是一个有几十个属性的完整对象。我的意思是,打字安全对你一点帮助都没有,因为你必须完全不同地对待它们。如果你不得不以不同的方式对待它们,那么把它们放在同一个变量中通常是没有意义的
items.forEach(item => {
  (item.product as Product)._id
})
if (item instanceof Product) { // do logic }}