ts的高级类型

TypeScript 的 高级类型(Advanced Types) 是指那些能够对类型进行复杂操作、组合和变换的类型系统特性。它们让你可以基于现有类型创建新类型,实现更强大、更安全的抽象。

1.交叉类型(intersection types):将多个类型合并为一个类型,新类型拥有所有类型的成员。常用于混入(mixins)或组合多个接口。

ts 复制代码
interface Person {
    name: string;
}

interface Employee {
    employeeId: number;
}

type EmployeePerson = Person & Employee;

const worker: EmployeePerson = {
    name: "Alice",
    employeeId: 1001
};

2.联合类型(union types):表示一个值可以是多种类型之一。

ts 复制代码
let id: string | number;
id = "abc"; //对
id = 123; //对
// id = true;  //错

function printId(id: string | number) {
  // 必须先进行类型检查
  if (typeof id === "string") {
    console.log(id.toUpperCase());
  } else {
    console.log(id.toFixed(2));
  }
}

3. 字符串字面量类型 (String Literal Types): 定义一个类型,其值只能是特定的字符串。

作用: 常用于创建类似枚举的效果,限制变量的取值范围。

ts 复制代码
type Direction = "up" | "down" | "left" | "right";
let move: Direction = "up"; // OK
console.log("move",move)
// move = 'up2'; // Error: Type '"up2"' is not assignable to type 'Direction'.

4.类型别名(type aliases):为类型创建一个新名字,可以是基本类型、联合、交叉、函数等。

ts 复制代码
type ID = string | number;
type Point = { x: number; y: number };
type Callback = (result: string) => void;

类型别名可以引用自己(递归类型):

type Tree<T> = {
    value: T;
    left: Tree<T> | null;
    right: Tree<T> | null;
};

5.类型保护和类型谓词(type guards):在运行时检查类型,从而在代码块中缩小类型范围。

1.typeof(查类型)守卫
ts 复制代码
function padLeft(value: string | number) {
    if (typeof value === "string") {
        return " " + value; // value: string
    }
    return Array(value).join(" ") + "0"; // value: number
}
2.instanceof 守卫
ts 复制代码
//先检查:如果 error 是一个真正的 Error 对象,那我再访问它的 .message 属性。

if (error instanceof Error) {
    console.log(error.message);
}
3.自定义类型守卫(使用 is
ts 复制代码
function isString(value: any): value is string {
    return typeof value === "string";
}

if (isString(input)) {
    // input: string
}
4. 可辨识联合(Discriminated Unions)

结合 联合类型 + 字面量类型 + 类型守卫,实现类型安全的模式匹配。

核心:通过检查一个共同的字面量属性来区分联合中的不同成员。

ts 复制代码
interface Square {
  kind: "square";
  size: number;
}
interface Rectangle {
  kind: "rectangle";
  width: number;
  height: number;
}
interface Circle {
  kind: "circle";
  radius: number;
}

type Shape = Square | Rectangle | Circle;

function area(s: Shape): number {
  switch (
    s.kind // 使用 'kind' 属性作为判别式
  ) {
    case "square":
      return s.size * s.size;
    case "rectangle":
      return s.width * s.height;
    case "circle":
      return Math.PI * s.radius ** 2;
  }
}
7.泛型

允许创建可以与多种类型一起工作的组件,实现类型安全的复用。

  • 语法 : 使用 <T> (T 是类型参数)。
  • 应用: 函数、接口、类、类型别名。
ts 复制代码
function identity<T>(arg: T): T {
    return arg;
}
let output = identity<string>("myString"); // output 是 string 类型
8.索引类型(Index Types)

利用keyofT[k]操作符,实现对对象属性的动态访问和类型安全。

keyof操作符:获取一个类型所有公共属性名的类型安全。

ts 复制代码
interface Person { name: string; age: number; }
type PersonKeys = keyof Person; // "name" | "age"

T[K]索引访问操作符:获取类型T上属性K的类型。

ts 复制代码
type PersonNameType = Person['name']; // string
in操作符(映射类型):遍历联合类型中的每个属性。
typeof操作符:获取一个值的类型。
ts 复制代码
const obj = { a: 1, b: 'hello' };
type ObjType = typeof obj; // { a: number; b: string }
9.映射类型(Mapped Types)

基于现有类型创建新类型,通过in操作符遍历keyof产生的联合类型。

常用内置映射类型:

  • Partial<T>: 将 T 的所有属性变为可选。
  • Readonly<T>: 将 T 的所有属性变为只读。
  • Pick<T, K>: 从 T 中选取一组属性 K,构成新类型。
  • Record<K, T>: 将 K 中的所有属性值都转换为 T 类型。
  • Omit<T, K>: 从 T 中剔除 K 的属性。
  • Exclude<T, U>: 从 T 中剔除可以赋值给 U 的类型。
  • Extract<T, U>: 从 T 中提取可以赋值给 U 的类型。
  • NonNullable<T>: 从 T 中剔除 null 和 undefined。
10.条件类型(Condditional Types)

使用T extends U ? X : Y 的语法,根据类型关系进行条件判断。

作用: 构建更复杂的类型逻辑。

ts 复制代码
type TypeName<T> = 
    T extends string ? "string" :
    T extends number ? "number" :
    T extends boolean ? "boolean" :
    T extends undefined ? "undefined" :
    T extends Function ? "function" :
    "object";
11.多态的this类型

在类中使用this作为返回类型,支持方法链式调用。

ts 复制代码
class BasicCalculator {
    constructor(protected value: number = 0) {}
    add(operand: number): this {
        this.value += operand;
        return this; // 返回 this,支持链式调用
    }
}
相关推荐
IT_陈寒22 分钟前
Vue3性能优化实战:这5个技巧让我的应用加载速度提升了70%
前端·人工智能·后端
树上有只程序猿23 分钟前
react 实现插槽slot功能
前端
stoneship1 小时前
Web项目减少资源加载失败白屏问题
前端
DaMu1 小时前
Cesium & Three.js 【移动端手游“户外大逃杀”】 还在“画页面的”前端开发小伙伴们,是时候该“在往前走一走”了!我们必须摆脱“画页面的”标签!
前端·gis
非专业程序员1 小时前
一文读懂Font文件
前端
Asort1 小时前
JavaScript 从零开始(七):函数编程入门——从定义到可重用代码的完整指南
前端·javascript
Johnny_FEer1 小时前
什么是 React 中的远程组件?
前端·react.js
我是日安1 小时前
从零到一打造 Vue3 响应式系统 Day 10 - 为何 Effect 会被指数级触发?
前端·vue.js
知了一笑1 小时前
「AI」网站模版,效果如何?
前端·后端·产品