javascript面向对象与原型浅析2

1、原型

所有函数都包含prototype(原型)属性,该属性是对象,所有实例共享该原型内的属性和方法。

//原型
function Person () {       //构造函数
    // body...
}
Person.prototype.name='zhangsan';
Person.prototype.age=26;
Person.prototype.sayHello=function(){
    return this.name+this.age+"Hello World...";
}
var person1=new Person();
person1.name='lisi';
person1.age=53

var person2=new Person();
alert(person1.sayHello==person2.sayHello); //返回true,因为他们保存的是指向原型sayHello函数的指针地址(如下图右图所示),而构造函数的话此处返回false
person1.email='lisi@163.com';  //增加属性
alert(person1.hasOwnProperty("email"));//判断实例中是否存在指定属性
delete person1.name;//删除实例属性是,使其访问原型里面改属性的值
alert(person1.name);//zhangsan delete Person.prototype.name //删除原型属性 alert(person1.name);//undefined alert(person1.sayHello());*/

------------------------------------------也可用下面方法创建原型--------------------------------------------------------------
function Person(){
}
Person.prototype={
    constructor:Person,//此处很重要,需要强制将constructor指向Person对象,默认不写的话,指向Object对象
name:"zhangsan",
    age:26,
    sayHello:function(){
      return this.name+this.age +"Hello World.....";
    }
}
PS:为什么不写constructor会指向Object?因为Person.prototype={};这种写法其实创建了一个新对象,每创建一个函数,会同时创建它的prototype,自动获取constructor属性,不重写的话constructor指向Object,重写的话,指向Person。

通过构造函数创建原型对象,不必再构造函数中定义对象信息,直接将信息添加到原型中 

 图解构造函数方式跟原型方式的不同:

__proto__属性是实例指向原型对象的一个指针,作用指向构造函数的原型属性constructor,通过这两个属性访问原型里的属性和方法。

原型模式的执行流程:

1.先查找构造函数实例里的属性或方法,如果有,立刻返回;

2.如果构造函数实例里面没有,则取原型对象里面查找,如果有,则返回;

原型最大的优点是实例化的所有对象都能共享属性、方法,然而这也是其最大的缺点,每个实例化对象初始化的值都是一样的,不具有独立性,如下面一段代码:

Person.prototype={
    constructor:Person,
    name:'zhangsan',
    age:50,
    family:['父亲','母亲','哥哥'],
    run:function(){
        return this.name+this.age+this.family;
    }
}

var person1=new Person();
person1.name='wangwu';
person1.age=60;
person1.family.push('弟弟');//给person1的家庭成员加入‘弟弟’
alert(person1.family);  // '父亲','母亲','哥哥','弟弟'
var person2=new Person();
person2.name='lisi';
person2.age=100;
alert(person2.family); // 这里也返回,'父亲','母亲','哥哥','弟弟',我们并不想让peron2的家庭成员里面也有弟弟,出现问题

 解决上面问题,我们需要用到下面一种方法:组合构造函数+原型模式

2、组合构造函数+原型模式

//组合构造函数+原型模式
function Person(name,age){       //构造函数
    this.name=name;
    this.age=age;
    this.family=['父亲','母亲','哥哥'];
}
Person.prototype={               //原型
    constructor:Person,
    run:function(){
        return this.name+this.age+this.family;
    }
}

var person1=new Person('zhangsan',10);
person1.family.push('弟弟');
alert(person1.family);//'父亲','母亲','哥哥','弟弟'
var person2=new Person('lisi',30);
alert(person2.run());//'父亲','母亲','哥哥'

PS:这种混合模式最大的好处是解决了传参和引用共享的问题,是创建对象比较好的方法,将需要共享的属性、方法放置在原型中,独立的属性、方法在构造函数中初始化。

原文地址:https://www.cnblogs.com/1017283242zhu/p/4519246.html