TypeScript中传参至函数后无法访问属性的问题排查
问题描述
定义了两个TypeScript接口:
interface Cat { name: string, color: string, feedingTimes: number[] } interface Dog { name: string, height: number, dateOfBirth: number, }
创建包含两种类型的数组:
const ANIMALS = [{...} as Cat, {...} as Dog]
遍历数组调用foo()函数:
ANIMALS.map((animal, index) => {foo(animal, identifier: getIdentifier(index))})
其中getIdentifier()根据索引返回字符串,foo()定义如下:
getIdentifier = (index: number):string => {...}; const foo = (animal: Cat | Dog) => { if(identifier === 'cat') { const {name, color, feeding} = animal } else { const {name, height, dateOfBirth} = animal } }
此时出现错误:无法解构animal的属性,提示“Property '...' does not exist on type 'Cat | Dog'”,求错误原因。
错误原因分析
- 类型守卫未建立关联:TypeScript无法将
identifier字符串的取值和animal的具体类型绑定。identifier是独立于animal的外部参数,TypeScript没有能力推断出identifier === 'cat'时animal一定是Cat类型,所以在分支里animal仍被视为Cat | Dog的联合类型。 - 联合类型的属性访问限制:对于联合类型
Cat | Dog,TypeScript只允许直接访问两者共有的属性(这里只有name)。像color(仅Cat拥有)、height(仅Dog拥有)这类专属属性,TypeScript无法确定当前animal是否具备,因此直接解构会报错。 - 代码存在语法与拼写错误:
foo函数未定义identifier参数,但在函数内部使用了该变量;调用foo时的传参语法错误,正确写法应为foo(animal, getIdentifier(index))。- 解构Cat属性时误写为
feeding,实际接口属性是feedingTimes,这也会导致属性不存在的错误。
内容的提问来源于stack exchange,提问作者four-eyes
相关产品推荐
相关产品推荐

