摘要:在本教程中,您将学习 TypeScript 中的类型守卫,以缩小变量的类型范围。
类型守卫允许您在条件块内缩小变量的类型范围。
typeof
让我们看一下以下示例
type alphanumeric = string | number;
function add(a: alphanumeric, b: alphanumeric) {
if (typeof a === 'number' && typeof b === 'number') {
return a + b;
}
if (typeof a === 'string' && typeof b === 'string') {
return a.concat(b);
}
throw new Error('Invalid arguments. Both arguments must be either numbers or strings.');
}
Code language: TypeScript (typescript)工作原理
- 首先,定义
alphanumeric类型,它可以保存字符串或数字。 - 接下来,声明一个函数,该函数将两个变量
a和b相加,它们的类型为alphanumeric。 - 然后,使用
typeof运算符检查两个参数的类型是否都是数字。如果是,则使用+运算符计算参数的总和。 - 之后,使用
typeof运算符检查两个参数的类型是否都是字符串。如果是,则连接两个参数。 - 最后,如果参数既不是数字也不是字符串,则抛出错误。
在这个示例中,TypeScript 了解typeof运算符在条件块中的使用。在以下if块中,TypeScript 意识到a和b是数字。
if (typeof a === 'number' && typeof b === 'number') {
return a + b;
}Code language: TypeScript (typescript)类似地,在以下if块中,TypeScript 将a和b视为字符串,因此您可以将它们连接成一个
if (typeof a === 'string' && typeof b === 'string') {
return a.concat(b);
}
Code language: TypeScript (typescript)instanceof
与typeof运算符类似,TypeScript 也知道instanceof运算符的使用。例如
class Customer {
isCreditAllowed(): boolean {
// ...
return true;
}
}
class Supplier {
isInShortList(): boolean {
// ...
return true;
}
}
type BusinessPartner = Customer | Supplier;
function signContract(partner: BusinessPartner) : string {
let message: string;
if (partner instanceof Customer) {
message = partner.isCreditAllowed() ? 'Sign a new contract with the customer' : 'Credit issue';
}
if (partner instanceof Supplier) {
message = partner.isInShortList() ? 'Sign a new contract the supplier' : 'Need to evaluate further';
}
return message;
}
Code language: TypeScript (typescript)工作原理
- 首先,声明
Customer和Supplier类。
其次,创建一个类型别名BusinessPartner,它是Customer和Supplier的联合类型。 - 第三,声明一个函数
signContract(),它接受一个类型为BusinessPartner的参数。 - 最后,检查合作伙伴是否是
Customer或Supplier的实例,然后提供相应的逻辑。
在以下if块中,由于instanceof运算符,TypeScript 知道合作伙伴是Customer类型的实例
if (partner instanceof Customer) {
message = partner.isCreditAllowed() ? 'Sign a new contract with the customer' : 'Credit issue';
}Code language: TypeScript (typescript)同样,TypeScript 知道合作伙伴是以下if块中的Supplier实例
if (partner instanceof Supplier) {
message = partner.isInShortList() ? 'Sign a new contract with the supplier' : 'Need to evaluate further';
}Code language: TypeScript (typescript)当 if 缩小一种类型时,TypeScript 知道在else中它不是那种类型,而是另一种类型。例如
function signContract(partner: BusinessPartner) : string {
let message: string;
if (partner instanceof Customer) {
message = partner.isCreditAllowed() ? 'Sign a new contract with the customer' : 'Credit issue';
} else {
// must be Supplier
message = partner.isInShortList() ? 'Sign a new contract with the supplier' : 'Need to evaluate further';
}
return message;
}
Code language: TypeScript (typescript)in
in运算符对对象上属性的存在进行安全检查。您也可以将其用作类型守卫。例如
function signContract(partner: BusinessPartner) : string {
let message: string;
if ('isCreditAllowed' in partner) {
message = partner.isCreditAllowed() ? 'Sign a new contract with the customer' : 'Credit issue';
} else {
// must be Supplier
message = partner.isInShortList() ? 'Sign a new contract the supplier ' : 'Need to evaluate further';
}
return message;
}
Code language: TypeScript (typescript)用户定义的类型守卫
用户定义的类型守卫允许您定义类型守卫或在使用函数时帮助 TypeScript 推断类型。
用户定义的类型守卫函数是一个函数,它只是返回arg is aType。例如
function isCustomer(partner: any): partner is Customer {
return partner instanceof Customer;
}
Code language: TypeScript (typescript)在这个示例中,isCustomer()是一个用户定义的类型守卫函数。现在您可以像下面这样使用它
function signContract(partner: BusinessPartner): string {
let message: string;
if (isCustomer(partner)) {
message = partner.isCreditAllowed() ? 'Sign a new contract with the customer' : 'Credit issue';
} else {
message = partner.isInShortList() ? 'Sign a new contract with the supplier' : 'Need to evaluate further';
}
return message;
}
Code language: TypeScript (typescript)总结
- 类型守卫在条件块中缩小了变量的类型范围。
- 使用
typeof和instanceof运算符在条件块中实现类型守卫
本教程是否有用?