覆盖派生的属性
将属性添加到对象时,无论它是否存在于原型中,该属性都会添加到对象本身中。 如果原型中已经有一个同名的属性,该属性将不再影响对象,因为它现在隐藏在对象自己的属性后面。
Rabbit.prototype.teeth = "small";console.log(killerRabbit.teeth);// → smallkillerRabbit.teeth = "long, sharp, and bloody";console.log(killerRabbit.teeth);// → long, sharp, and bloodyconsole.log(blackRabbit.teeth);// → smallconsole.log(Rabbit.prototype.teeth);// → small
下图简单地描述了代码执行后的情况。其中Rabbit和Object原型画在了killerRabbit之下,我们可以从原型中找到对象中没有的属性。

覆盖原型中存在的属性是很有用的特性。就像示例展示的那样,我们覆盖了killerRabbit的teeth属性,这可以用来描述实例(对象中更为泛化的类的实例)的特殊属性,同时又可以让简单对象从原型中获取标准的值。
覆盖也用于向标准函数和数组原型提供toString方法,与基本对象的原型不同。
console.log(Array.prototype.toString ==Object.prototype.toString);// → falseconsole.log([1, 2].toString());// → 1,2
调用数组的toString方法后得到的结果与调用.join(",")的结果十分类似,即在数组的每个值之间插入一个逗号。而直接使用数组调用Object.prototype.toString则会产生一个完全不同的字符串。由于Object原型提供的toString方法并不了解数组结构,因此只会简单地输出一对方括号,并在方括号中间输出单词"object"和类型的名称。
console.log(Object.prototype.toString.call([1, 2]));// → [object Array]
