MST

星途 面试题库

面试题:TypeScript 中复杂对象类型的上下文类型推断

定义一个包含多个属性且属性类型不同的复杂对象类型 `UserInfo`,其中有 `name`(字符串类型)、`age`(数字类型)、`isAdmin`(布尔类型)。编写一个函数 `processUser`,它接收 `UserInfo` 类型的参数,并根据不同属性进行不同操作(例如 `isAdmin` 为 `true` 时打印特定信息)。在调用 `processUser` 函数时,不明确指定传入对象的类型,依靠上下文类型推断。请解释为什么上下文类型推断能够成功,以及在这个场景下可能会遇到的类型相关问题及解决办法。
16.7万 热度难度
前端开发TypeScript

知识考点

AI 面试

面试题答案

一键面试

1. 定义 UserInfo 类型和 processUser 函数

// 定义 UserInfo 类型
type UserInfo = {
    name: string;
    age: number;
    isAdmin: boolean;
};

// 定义 processUser 函数
function processUser(user: UserInfo) {
    if (user.isAdmin) {
        console.log(`${user.name} 是管理员`);
    } else {
        console.log(`${user.name} 不是管理员`);
    }
}

2. 调用 processUser 函数并依靠上下文类型推断

// 调用函数,依靠上下文类型推断
processUser({ name: '张三', age: 30, isAdmin: true });

3. 上下文类型推断成功的原因

在 TypeScript 中,上下文类型推断是基于表达式所处的位置来推断类型。当调用 processUser 函数时,TypeScript 会根据函数参数的期望类型(UserInfo),对传入的对象字面量进行类型检查。如果对象字面量的形状(shape)与期望类型匹配,TypeScript 就可以推断出该对象的类型,即使没有显式指定。

4. 可能遇到的类型相关问题及解决办法

  • 问题:属性缺失
    • 描述:如果传入的对象字面量缺少 UserInfo 类型中的某个属性,例如 { name: '李四', isAdmin: false } 缺少 age 属性,TypeScript 会报错。
    • 解决办法:确保传入的对象字面量包含 UserInfo 类型定义的所有属性。
  • 问题:属性类型不匹配
    • 描述:如果传入的对象字面量中某个属性的类型与 UserInfo 类型定义的不一致,例如 { name: '王五', age: 'twenty', isAdmin: true }age 是字符串类型,TypeScript 会报错。
    • 解决办法:确保传入对象字面量的每个属性类型与 UserInfo 类型定义的一致。
  • 问题:额外属性
    • 描述:如果传入的对象字面量包含 UserInfo 类型中没有定义的额外属性,例如 { name: '赵六', age: 25, isAdmin: false, gender: '男' },虽然这在 JavaScript 中是合法的,但在严格的 TypeScript 模式下可能会报错(取决于 noExtraProperties 等编译选项)。
    • 解决办法:如果需要允许额外属性,可以使用索引签名([propName: string]: any)来定义 UserInfo 类型,但这会失去对额外属性类型的严格检查;或者使用类型断言 as UserInfo 来告诉 TypeScript 这个对象符合 UserInfo 类型,忽略额外属性。不过这两种方法都要谨慎使用,以免引入运行时错误。