面试题答案
一键面试相同点
类型保护和类型守卫本质上都是用于在运行时确定变量的类型,以便 TypeScript 能够在特定代码块中更准确地进行类型检查,让开发者可以安全地访问特定类型的属性和方法。
不同点
- 类型保护:是一个更宽泛的概念,指任何可以在运行时缩小变量类型范围的表达式。它可以基于多种条件,如
typeof
、instanceof
检查等。 - 类型守卫:通常是指自定义的类型保护函数,通过函数返回值来缩小变量类型范围。其函数返回值类型必须是一个类型谓词
parameterName is Type
。
类型保护示例
function printValue(value: string | number) {
if (typeof value === 'string') {
console.log(value.length); // 在这个代码块内,TypeScript 知道 value 是 string 类型,可访问 length 属性
} else {
console.log(value.toFixed(2)); // 在这个代码块内,TypeScript 知道 value 是 number 类型,可访问 toFixed 方法
}
}
printValue('hello');
printValue(123);
这里 typeof value ==='string'
就是一个类型保护,它在运行时检查 value
的类型,从而让 TypeScript 能在不同分支准确识别类型。
类型守卫示例
interface Bird {
fly: () => void;
layEggs: () => void;
}
interface Fish {
swim: () => void;
layEggs: () => void;
}
function isBird(animal: Bird | Fish): animal is Bird {
return (animal as Bird).fly!== undefined;
}
function handleAnimal(animal: Bird | Fish) {
if (isBird(animal)) {
animal.fly(); // 在这个代码块内,TypeScript 知道 animal 是 Bird 类型,可访问 fly 方法
} else {
animal.swim(); // 在这个代码块内,TypeScript 知道 animal 是 Fish 类型,可访问 swim 方法
}
}
这里 isBird
函数就是一个类型守卫,通过返回 animal is Bird
这种类型谓词,在 handleAnimal
函数中缩小 animal
的类型范围,使 TypeScript 能准确识别类型。