在默认的情况下,所有的原型对象都会自动获得一个constructor(构造函数)属性,这个属性包含一个指向prototype属性所在函数的指针。如下图
function Person(){ }
上图的js代码就是
Person.prototype={ name:"Nicholas", age:23, sayName:function(){ return this.name; } };
var p1=new Person();
当创建一个新的p2之后依然会有一个_proto_属性指向Person的原型(Persion.prototype),换句话说每个实例与构造函数没有直接的关系,虽然这实例都不包含属性和方法,但我们却可以调用p1.name查找对象属性的个过程来实现。此时如果通过p2.name设置属性值后会在对象自己的内存空间中存储name的值,当调用sayName()方法的时候在寻找name时,在自己空间中找到之后就不会去原型对象中查找(注意:原型中的值是不会被替换,仅仅是在查找的时候被覆盖)
var p1=new Person(); alert(p1.name);//Nicholas var p2=new Person();
//检查某个对象是否是某个函数的原型 alert(Person.prototype.isPrototypeOf(p1));//true ECMAScript5中增加一个新的方法.叫做Object.getPrototypeOf(),在所有支持的实现中,这个方法返回[[Prototype]]的值 alert(Object.getPrototypeOf(p1)==Person.prototype); alert(Object.getPrototypeOf(p1).name); //alert(p1.constructor==Person); //alert(p2.hasOwnProperty("name")) delete p2.name; //alert("name" in p1)//来自原型 p1.id=12; // alert("id" in p1);//来自实例 alert(hasPrototypeProperty(p1,"name")) /** 检查某个属性是否在原型中存在 */ function hasPrototypeProperty(obj,prop){ return ((!obj.hasOwnProperty(prop))&&(prop in obj)); }
var p2=new Person(); Person.prototype.sayHi=function(){ alert(this.name); } p2.sayHi();//可以获取值
function Person(){ } var p1=new Person(); //所有的"范围对象"都继承自这个对象 重写原型对象 Person.prototype.sayHi=function(){ alert(this.name); } //所有的"范围对象"都继承自这个对象 重写原型对象 Person.prototype={ constructor:Person,//显示的设置构造函数的反向引用 name:"Nicholas", age:23, sayName:function(){ return this.name; } }; p1.sayHi();//undefined alert(p1.sayName());//报错 var p2=new Person(); alert(p2.sayName());//Nichola
原型存在的问题
原型对象中的属性是被很多实例共享的,这个共享对于函数是非常合适的,对于原型中基本值得属性是没有问题的但是,如果属性值包含引用类型值就会有一定的问题了。
function Person(){ } Person.prototype={ constructor:Person,//显示的设置构造函数的反向引用 name:"Nicholas", age:23, friends:["Shelby","Cunrt"], sayName:function(){ return this.name; } }; var p1=new Person(); var p2=new Person(); p1.friends.push("Jack"); alert(p1.friends);//"Shelby","Cunrt","Jack" alert(p2.friends);//"Shelby","Cunrt","Jack" alert(p1.friends==p2.friends);//true
function Person(name,age,friends){ this.name=name; this.age=age; this.friends=friends; } Person.prototype={ constructor:Person,//显示的设置构造函数的反向引用 sayName:function(){ return this.name; } }; var p1=new Person("Tom",20,"Shelby"); var p2=new Person("Alisa",20,["Cunrt","Jack"]); alert(p1.friends);//"Shelby" alert(p2.friends);//"Cunrt","Jack" alert(p1.friends==p2.friends);//false
对Javascript中原型的深入理解,布布扣,bubuko.com
原文:http://blog.csdn.net/zl_jay/article/details/25808969