JavaSctipt之prototype原型深入分析: prototype的属性是副本,引用,还是固定的查找方式?
----01_修改prototype的属性
//
<script type="text/javascript">
var Person = function()
{
};
Person.prototype.username = new String("zhangsan");
var person1 = new Person();
var person2 = new Person();
alert("实例创建后,person1.username: "+person1.username);
alert("实例创建后,person2.username: "+person2.username);
//修改原型的属性值:
Person.prototype.username = new String("lisi");
alert("原型被修改后,person1.username: "+person1.username);
alert("原型被修改后,person2.username: "+person2.username);
</script>
//
输出:
实例创建后,person1.username: zhangsan
实例创建后,person2.username: zhangsan
原型被修改后,person1.username: lisi
原型被修改后,person2.username: lisi
问题: 为什么原型的属性值被修改后,2个实例person1,person2的属性值也变了呢?
假设1副本:
N个实例创建时都持有原型的属性的副本,原型的属性被修改后,接着进行修改N个实例上的属性值(进行N次修改).
这样在原型的属性值改变后,同时修改实例上的副本的值.
--要进行N次修改,这个应该不太可能吧!
假设2引用:
N个实例创建时都持有原型的属性的引用,此时Person.prototype.username 和 person.username 都是引用同一个对象String("zhangsan"),当Person.prototype.username = new String("lisi")执行后,Person.prototype.usename引用新的对象String("lisi"),接着修改N个实例上的username属性,使其username也引用同一个对象:String("lisi").
这样原型的属性引用新对象后,实例的属性也引用同一个新对象.
--要进行N次修改,这个可能性也不高.
假设3固定查找方式:
N个实例创建时没有原型同名的属性,如person创建时,它自身并没有username属性! 当访问person.username时,因为它自身并没有username属性,所以按照固定的查找方式来查找:
因为person是Person的实例(person instanceof Person 得到的是true),所以查找Person.prototype的属性,如果没找到,继续向上一层原型查找,在这里,js引擎找到了Person.prototype.username属性,故输出!
因为这个查找方式,当修改原型的属性值Person.prototype.username后,并不需要进行额外的操作!
所以原型的属性值被修改为"lisi"后,person1.username查找到的也是原型的属性值!
--仅需修改prototype,然后按固定查找方式查找,能解译此例!
返回全文