跳到主要内容

TypeScript 类型系统深入

介绍

TypeScript 是一种强类型的 JavaScript 超集,它的类型系统是其最强大的特性之一。通过类型系统,开发者可以在编写代码时捕获潜在的错误,并提高代码的可读性和可维护性。本文将深入探讨 TypeScript 类型系统的核心概念,帮助初学者理解并掌握这些高级主题。

类型推断

TypeScript 的类型推断功能使得开发者无需显式声明类型,TypeScript 会根据上下文自动推断出变量的类型。例如:

typescript
let num = 42; // TypeScript 推断 num 的类型为 number
let str = "Hello"; // TypeScript 推断 str 的类型为 string
提示

类型推断可以简化代码,但在某些情况下,显式声明类型可以提高代码的可读性。

联合类型与交叉类型

联合类型

联合类型允许一个变量具有多种类型。使用 | 符号来定义联合类型:

typescript
let value: string | number;
value = "Hello"; // 合法
value = 42; // 合法
value = true; // 错误:boolean 不是 string 或 number 类型

交叉类型

交叉类型允许将多个类型合并为一个类型。使用 & 符号来定义交叉类型:

typescript
type Person = { name: string };
type Employee = { employeeId: number };

type EmployeeRecord = Person & Employee;

const employee: EmployeeRecord = {
name: "Alice",
employeeId: 12345,
};
备注

交叉类型通常用于组合多个接口或类型,以创建更复杂的类型。

类型别名与接口

类型别名

类型别名允许你为类型创建一个新的名称。使用 type 关键字来定义类型别名:

typescript
type StringOrNumber = string | number;

let value: StringOrNumber;
value = "Hello"; // 合法
value = 42; // 合法

接口

接口用于定义对象的形状。使用 interface 关键字来定义接口:

typescript
interface Person {
name: string;
age: number;
}

const person: Person = {
name: "Bob",
age: 30,
};
警告

类型别名和接口在某些情况下可以互换使用,但接口更适合定义对象的形状,而类型别名更适合定义联合类型或交叉类型。

条件类型

条件类型允许你根据条件选择类型。使用 extends 关键字和三元运算符来定义条件类型:

typescript
type IsString<T> = T extends string ? true : false;

type A = IsString<"hello">; // true
type B = IsString<42>; // false
提示

条件类型在泛型和高级类型操作中非常有用,可以帮助你根据输入类型动态选择输出类型。

实际案例

案例1:处理API响应

假设你正在处理一个API响应,该响应可能返回一个用户对象或一个错误对象。你可以使用联合类型来处理这种情况:

typescript
type User = { id: number; name: string };
type ErrorResponse = { error: string };

type ApiResponse = User | ErrorResponse;

function handleResponse(response: ApiResponse) {
if ("error" in response) {
console.error(response.error);
} else {
console.log(`User: ${response.name}`);
}
}

案例2:动态表单验证

假设你正在开发一个动态表单验证系统,你可以使用条件类型来根据输入类型选择验证规则:

typescript
type ValidationRule<T> = T extends string ? { minLength: number } : { minValue: number };

function validate<T>(value: T, rule: ValidationRule<T>) {
if (typeof value === "string") {
return value.length >= rule.minLength;
} else {
return value >= rule.minValue;
}
}

const isValidString = validate("hello", { minLength: 3 }); // true
const isValidNumber = validate(42, { minValue: 50 }); // false

总结

TypeScript 的类型系统提供了强大的工具来帮助开发者编写更安全、更可维护的代码。通过理解类型推断、联合类型、交叉类型、类型别名、接口和条件类型,你可以更好地利用 TypeScript 的类型系统来提升你的开发效率。

附加资源与练习

  • 练习1:尝试定义一个联合类型,表示一个变量可以是字符串、数字或布尔值。
  • 练习2:创建一个接口 Car,包含 makemodelyear 属性,并创建一个类型别名 CarOrTruck,表示 CarTruck 类型。
  • 附加资源

通过不断练习和探索,你将能够更深入地理解 TypeScript 的类型系统,并在实际项目中灵活运用这些高级类型技巧。