MST

星途 面试题库

面试题:深入理解TypeScript中super的底层原理及应用场景

阐述TypeScript中super关键字背后的底层原理,包括它如何与JavaScript的原型链交互以及在装饰器等高级特性下的表现。同时,列举至少两个在实际项目开发中利用super实现独特功能的场景,并详细说明实现思路。
28.4万 热度难度
前端开发TypeScript

知识考点

AI 面试

面试题答案

一键面试

TypeScript 中 super 关键字的底层原理

  1. 与 JavaScript 原型链的交互
    • 在 JavaScript 中,基于原型链的继承是实现对象间属性和方法共享的重要机制。super 关键字在类继承的场景下,用于访问和调用父类的属性、方法。
    • 当子类实例化时,其 [[Prototype]] 指向父类的实例(通过 Object.setPrototypeOf(subClass.prototype, superClass.prototype) 这样的机制)。super 提供了一种访问父类实例上属性和方法的方式。例如,在子类方法中使用 super.method(),它会在父类的原型链上查找 method 方法并执行。
    • 在构造函数中,super() 用于调用父类的构造函数。这是必要的,因为子类构造函数在访问 this 之前,必须先调用父类构造函数来初始化继承自父类的属性,确保原型链的正确构建。
  2. 在装饰器等高级特性下的表现
    • 装饰器与 super:装饰器可以用来修改类、方法、属性等的行为。当在被装饰的类中使用 super 时,需要注意装饰器可能对原型链和类结构的影响。例如,一个方法装饰器可能会修改方法的执行逻辑,但 super 依然是基于原始的父类原型链来访问父类方法。
    • 类装饰器场景:假设一个类装饰器给类添加了一些额外的属性或方法。子类使用 super 时,仍然是访问父类未经装饰器修改前的原型链上的属性和方法。这是因为 super 的解析是基于类定义时的原型链结构,而不是基于运行时被装饰器修改后的类结构。

实际项目开发中利用 super 实现独特功能的场景

  1. 场景一:重写并增强父类方法
    • 实现思路:在很多项目中,可能需要在子类中对父类的某个方法进行扩展。例如,有一个父类 Logger 用于记录简单日志,子类 EnhancedLogger 想要在记录日志的同时发送通知。
    • 代码示例
class Logger {
    log(message: string) {
        console.log(`Log: ${message}`);
    }
}

class EnhancedLogger extends Logger {
    log(message: string) {
        super.log(message);
        // 发送通知逻辑
        console.log(`Sending notification for: ${message}`);
    }
}
  • 在这个例子中,EnhancedLogger 重写了 log 方法。通过 super.log(message) 先执行父类的日志记录逻辑,然后再添加自己的发送通知逻辑,实现了功能的增强。
  1. 场景二:复用父类的初始化逻辑
    • 实现思路:在创建复杂对象层次结构时,子类可能需要复用父类的构造函数逻辑来初始化一些基础属性。例如,有一个父类 User 包含基本的用户信息属性,子类 AdminUser 除了这些基本属性外还有管理员特有的权限属性。
    • 代码示例
class User {
    name: string;
    age: number;
    constructor(name: string, age: number) {
        this.name = name;
        this.age = age;
    }
}

class AdminUser extends User {
    permissions: string[];
    constructor(name: string, age: number, permissions: string[]) {
        super(name, age);
        this.permissions = permissions;
    }
}
  • AdminUser 的构造函数中,通过 super(name, age) 调用父类 User 的构造函数来初始化 nameage 属性,然后再初始化自己特有的 permissions 属性,避免了在子类构造函数中重复编写父类的初始化逻辑。