例:我们需要得到一组不同边长的正方形,并计算他的面积和周长
最初我们可能会写出这样的代码
这些代码可以解决问题,但是它的缺陷在于每一次调用getArea()、getLength()函数时,都会开辟新的内存空间,因为边长的不同,函数都各不相同,但是其实他们是同一形式的,这样未免太过于浪费内存。
let squareList = [];let widthList = [5, 6, 5, 6, 5, 6, 5, 6, 5, 6, 5, 6];for (let i = 0; i < 12; i++) {squareList[i] = {width: widthList[i],getArea() {return this.width * this.width;//每一次的调用都是不一样的},getLength() {return this.width * 4;},};}
学会声明函数和原型进行对象的(批量)创建
为了将同一形式的函数进行集成,使每一次调用都不必开辟新的内存空间,可以使用函数和原型,并通过函数的原型是代码更加整体化
function createSquare(width) {//其实就是构造函数
let obj = Object.create(createSquare.squarePrototype);
obj.width = width;
return obj;
}
createSquare.squarePrototype = {//其实不必使用函数的原型(使用其他的名字也可以,如common)这样使
getArea() { //代码更加集成,整体化,但是new操作符设定是构造函数的prototype
return this.width * this.width;
},
getLength() {
return this.width * 4;
},
constructor: createSquare,//用来原型所属的构造器
};
let square = createSquare(5);
new命令的作用
在使用new命令配合构造函数进行对象创建时,new操作符会自动进行以下工作
以new X( )为例
- new命令会自动创建一个空对象
- new命令会将这个空对象与其构造函数的原型相联系,为X.prototype(使得我们写完对象的原型后不必再使用Object.create()方法,以及constructor的设置)
- new命令会将this关键字指向空对象
- new命令执行构造函数中的代码并会返回创建的对象(如果构造函数中有return语句,且return了一个对象,new命令就会返回这个对象,否则就会返回生成的对象)
- 如果构造函数中没有this关键字,new命令会返回一个空对象
- new.target 函数内部可以使用new.target属性,来判断函数是否是new命令调用,使用new命令时,返回的是当前函数,否则返回undefined
因此我们需要的工作就是为X()构造函数添加属性以及设置对象的原型来保存共用属性。因此上例就变成了
function Square(width) {
this.width = width;
}
Square.prototype.getArea = function () {//通过原型的设置保存共用属性
return this.width * this.width;
};
Square.prototype.getLength = function () {
return this.width * 4;
};
let square = new Square(5);
