ThinkChat2.0新版上线,更智能更精彩,支持会话、画图、阅读、搜索等,送10W Token,即刻开启你的AI之旅 广告
## 一、概述 JavaScript 语言中,生成实例对象的传统方法是通过构造函数。 ``` function Point(x, y) { this.x = x; this.y = y; } Point.prototype.toString = function () { return '(' + this.x + ', ' + this.y + ')'; }; var p = new Point(1, 2); ``` ES6 提供了更接近传统语言的写法,引入了 Class(类)这个概念,作为对象的模板。通过`class`关键字,可以定义类。 ``` class Point { constructor(x, y) { this.x = x; this.y = y; } toString() { return '(' + this.x + ', ' + this.y + ')'; } } ``` ## 二、constructor `constructor`方法是类的默认方法,通过`new`命令生成对象实例时,自动调用该方法。一个类必须有`constructor`方法,如果没有显式定义,一个空的`constructor`方法会被默认添加。 ``` class Point { } // 等同于 class Point { constructor() {} } ``` ## 三、prototype 属性和__proto__属性 大多数浏览器的 ES5 实现之中,每一个对象都有__proto__属性,指向对应的构造函数的prototype属性。Class 作为构造函数的语法糖,同时有prototype属性和__proto__属性,因此同时存在两条继承链。 (1)子类的__proto__属性,表示构造函数的继承,总是指向父类。 (2)子类prototype属性的__proto__属性,表示方法的继承,总是指向父类的prototype属性。 ``` class A { } class B extends A { } B.__proto__ === A // true B.prototype.__proto__ === A.prototype // true ``` ``` class A { } class B { } // B 的实例继承 A 的实例 Object.setPrototypeOf(B.prototype, A.prototype); // B 继承 A 的静态属性 Object.setPrototypeOf(B, A); const b = new B(); ``` ## 四、extends继承 Class 可以通过`extends`关键字实现继承; ``` class Point { } class ColorPoint extends Point { } ``` ## 五、Object.getPrototypeOf Object.getPrototypeOf方法可以用来从子类上获取父类。 ``` Object.getPrototypeOf(ColorPoint) === Point // true ``` ## 六、super super这个关键字,既可以当作函数使用,也可以当作对象使用。在这两种情况下,它的用法完全不同。 第一种情况,super作为函数调用时,代表父类的构造函数。ES6 要求,子类的构造函数必须执行一次super函数。 ``` class A {} class B extends A { constructor() { super(); } } ``` 作为函数时,`super()`只能用在子类的构造函数之中,用在其他地方就会报错。 ``` class A {} class B extends A { m() { super(); // 报错 } } ```