单例模式
全局有且仅有一个实例对象(比如vue/react全局路由对象)
new做了什么操作
- 结构上:创建一个空对象,作为返回的对象实例
- 属性上:将生成空对象的原型对象属性指向了构造函数的prototype属性
- 关系上:将当前实例对象赋值给了内部的this
- 生命周期上:执行了构造函数的初始化代码
手写实现一个new
function userNew(obj, ...args) {
const newObj = Object.create(obj.prototype);
const result = obj.apply(newObj, args);
return typeof result === 'object' ? result : newObj;
}
constructor是什么
- 每个对象在创建时,会自动拥有一个构造函数constructor属性
- constructor源自原型对象,指向了构造函数的引用
原型对象
function Course() {};
const course1 = new Course();
const course2 = new Course();
* 1. course1.__proto__ = Course.prototype;
* 2. course1.constructor = Course;
js如何实现继承
原型链继承
// 在原型对象的所有属性和方法,都可以被实例所继承
* 1. 属性挂载在模板(类)上,方法挂载在原型上
function Game() {
this.name = 'lol';
}
Game.propotype.getName = function() {
return this.name;
}
// LOL
function LOL() {};
LOL.prototype = new Game();
LOL.prototype.constructor = LOL;
const game = new LOL();
// 本质:重写了原型对象方式,将父对象的属性方法,作为自对象原型的属性方法,同时重写构造函数
// 原型链直接继承有什么缺陷吗
* 1. 父类存在引用类型属性时,被其中一个子类更改后,会影响到所有使用该属性的子类
* 2. 子类无法向父类进行传参
// 如何解决--构造函数继承
构造函数继承
function Game(args) {
this.name = 'lol';
}
Game.propotype.getName = function() {
return this.name;
}
// LOL
function LOL(args) {
Game.call(this, args)
};
const game3 = new LOL('args');
// 解决了共享属性+子向父传参问题
// 存在问题 原型链上的方法无法被继承 如何解决--组合继承
组合继承
function Game(args) {
this.name = 'lol';
}
Game.propotype.getName = function() {
return this.name;
}
// LOL
function LOL(args) {
Game.apply(this, args)
};
LOL.proptotype = new Game();
LOL.proptotype.constructor = LOL;
const game4 = new LOL('args');
// 组合继承就没有问题了吗? 问题在于无论何种场景,都会调用两次父类构造函数
// 解决办法 寄生组合式继承
寄生组合式继承
function Game(args) {
this.name = 'lol';
}
Game.propotype.getName = function() {
return this.name;
}
// LOL
function LOL(args) {
Game.apply(this, args)
};
LOL.proptotype = Object.create(Game.prototype);
LOL.proptotype.constructor = LOL;
const game5 = new LOL('args');
如何实现多重继承
function Game(args) {
this.name = 'lol';
}
Game.propotype.getName = function() {
return this.name;
}
function Store() {
this.shop = 'steam';
}
function LOL(args) {
Game.call(this, args);
Store.call(this, args);
};
LOL.proptotype = Object.create(Game.prototype);
Object.assin({
Store.prototype,
LOL.prototype
});
LOL.proptotype.constructor = LOL;