关于new操作符,我们最常看到的代码像这样:
var obj = new Base();
new操作符具体干了什么呢?我们可以用代码模拟它的行为。
var obj = (function () {
var temp = {};
temp.__proto__ = Base.prototype;
var result = Base.call(temp);
return typeof result === 'object'? result : temp;
})();
- 创建了一个空对象obj。
- 将这个空对象的__proto__成员指向了Base函数对象prototype成员对象。
- 将Base函数对象的this指针替换成obj,然后再调用Base函数。
- 判断result的类型,返回结果。
下面通过一些例子来理解
在没有return的情况下
function A() {
this.a = 'a';
}
var a = new A();
console.log(a); //A {a: "a"}
console.log(a.__proto__.constructor); //ƒ A() {this.a = 'a';}
function B() {
var b = 'b'
}
var b = new B();
console.log(b); //B {}
console.log(b.__proto__.constructor); //ƒ B() {var b = 'b'}
由以上的结果可以分析出
- 实例的constructo都指向构造函数。
在有return的情况下
function C() {
return 'c';
}
var c = new C();
console.log(c); //C {}
console.log(c.__proto__.constructor);//ƒ C() {return 'c';}
function D() {
return {
d: 'd'
};
}
var d = new D();
console.log(d); //{d: "d"}
console.log(d.__proto__.constructor);//ƒ Object() { [native code] }
function E() {
return function () {
this.e = 'e';
}
}
var e = new E();
console.log(e); //ƒ () {this.e = 'e';}
console.log(e.__proto__.constructor);//ƒ Function() { [native code] }
function F() {
this.f = 'f';
return {
f: 'f-1'
}
}
var f = new F();
console.log(f); //{f: "f-1"}
console.log(f.__proto__.constructor);//ƒ Object() { [native code] }
function G() {
return gv;
}
var g = new G();
console.log(gv === g); //true
由以上的结果可以分析出
- 正如编辑器webstorm的提示语(Primitive value returned from constructor will be lost when called with 'new')所说的一样, 如果return的是一个基本类型的值,那么值会消失,new出来的实例就是一个空对象,实例的constructor指向构造函数。
- 如果return的是一个引用类型的值,那么new出来的实例就是就是return的值的本身,实例的constructor指向值的constructor。