手动实现一个new
-
首先来看一个案列
function Dog (name,age){ this.name = name; this.age = age; this.say = function () { console.log("I am " + this.name) } } var dog = new Dog('旺财',4) console.log(dog) // Dog {name: "旺财", age: 4, say:f }
这一过程实际是:在
new
的时候,实际是去调用了构造函数Dog
里面的constructor
构造器,最后返回一个新的对象,这个new
出来的实例继承了构造函数的属性和方法,这一过程手动实现大致可以分为以下几步- 获取构造函数
- 把对象的
__proto__
指向构造函数的原型对象prototype
- 绑定
this
到obj
(指向新生成的实例对象) ,并传递参数 - 返回(产生)了一个新的对象
-
手动实现
function self_New () {
// 创建一个新对象:两种方式都可以
// var obj = {}
var obj = new Object();
// 获得构造函数
[ Con, ...arg ] = arguments
// 链接到原型(给obj这个新生对象的原型指向它的构造函数的原型,使其可以获取到构造函数上的属性和方法)
obj.__proto__ = Con.prototype;
// 绑定this到obj,并传递参数(call形式)
var result = Con.call(obj,...arg);
// 绑定this到obj,并传递参数(apply形式)
// var result = Con.apply(obj,[...arg]);
// 确保new出来的是一个对象
return typeof result === "object" ? result : obj
}
// 使用
var dog2 = self_New (Dog,'旺财',4);
console.log('dog2',dog2) // dog2: {name: "旺财", age: 4, say:f }
总结:
- 对于创建一个对象来说,更推荐使用字面量的方式创建对象(性能和可读性)。因为你使用
new Object()
的方式创建对象需要通过作用域链一层层找到Object
,但是你使用字面量的方式就没这个问题