MST

星途 面试题库

面试题:TypeScript类型守卫与类型断言在复杂类型结构中的应用

假设有一个联合类型 `type MixedType = { type: 'object'; value: { [key: string]: any } } | { type: 'array'; value: any[] } | { type:'scalar'; value: string | number }`,编写一个函数 `processValue`,该函数接收 `MixedType` 类型的参数,使用类型守卫和类型断言来处理不同类型的值,并执行以下操作:如果是 `object` 类型,返回其所有属性名组成的数组;如果是 `array` 类型,返回数组长度;如果是 `scalar` 类型,返回值的字符串形式。同时阐述在这种复杂类型结构下,类型守卫和类型断言的使用要点及可能遇到的陷阱。
34.7万 热度难度
前端开发TypeScript

知识考点

AI 面试

面试题答案

一键面试
function processValue(value: MixedType): string[] | number | string {
    if (value.type === 'object') {
        return Object.keys(value.value);
    } else if (value.type === 'array') {
        return value.value.length;
    } else if (value.type ==='scalar') {
        return value.value.toString();
    }
}

类型守卫和类型断言的使用要点

  1. 类型守卫
    • 在上述代码中,通过 if (value.type === 'object') 等条件判断来作为类型守卫。类型守卫的要点在于利用类型中的某个属性(如这里的 type)来明确地缩小类型范围。通过这种方式,TypeScript 能够在 if 代码块内确定 value 的具体类型,从而允许对特定类型的属性和方法进行安全访问。例如在 if (value.type === 'object') 块内,value.value 可以安全地使用 Object.keys 方法,因为此时 value.value 被明确为 { [key: string]: any } 类型。
  2. 类型断言
    • 在这种情况下,虽然代码中没有显式使用类型断言,但类型断言在复杂类型结构中也很重要。当 TypeScript 无法通过类型守卫完全推断出类型时,类型断言可用于手动指定类型。例如,如果有一个函数返回 any 类型,但你知道它实际返回的是 MixedType 中的某一种类型,你可以使用类型断言 (result as { type: 'object'; value: { [key: string]: any } }) 来明确类型,以便后续进行正确的操作。

可能遇到的陷阱

  1. 类型守卫判断不全面
    • 如果遗漏了某些 type 值的判断,例如没有处理 if (value.type ==='scalar'),那么对于 scalar 类型的值,函数将无法正确处理,可能返回 undefined 或者抛出运行时错误。
  2. 类型断言错误
    • 如果类型断言使用不当,例如将一个实际不是 object 类型的值断言为 { type: 'object'; value: { [key: string]: any } } 类型,在后续访问 value 的属性时就会抛出运行时错误,因为实际类型不具备相应的属性结构。
  3. 类型变化未更新
    • 如果 MixedType 的联合类型发生变化,例如新增了一种 type'newType' 的情况,而类型守卫和函数逻辑没有相应更新,就会导致新类型的值无法正确处理。