我们知道JS有对象,举个栗子:
var obj = { name : 'obj' }
我们可以对obj进行一些操作,包括以下的操作:
-【增】
-【删】
-【改】
-【查】
下面我们来看看我们写的那行代码通过控制台打印出来是什么样子的
通过上面的图片我们发现
obj
已经有几个方法了(属性),但是我画红线的部分,我们并没有写,没有给赋值,那是valueOf
怎么来的呢?
通过控制台打印出来的结果的是:
- obj 有一个属性 name (这是我们自己写的)
- obj 有一个属性叫做proto (这是一个对象)
3.obj还有其他的想toString、constructor、还有我们的valueOf等属性
我们的问题是我们没有给这些属性,那这些属性是从哪里来的呢?
答案:从这个proto身上来的
当我们【查找】 obj.valueOf
的时候,浏览器会做下面的事情:
先从obj的本身上面来看有没有我们要的
valueOf
的属性。没有就会进行下一步,看看
obj.__proto__
对象里面有没有valueOf
属性,发现obj.__proto__
有个valueOf
的属性,于是就找到了,所以我们浏览器中看到的其实是在第二步中看到的,obj.__proto__.valueOf
。
3.如果obj.__proto__
对象里面没有,那么浏览器会继续查看obj.__proto__.__proto__
。
4.如果obj.__proto__.__proto__
里面还是没有的话,浏览器就会继续的往下寻找obj.__proto__.__proto__.__proto__
。
5.直到找到valueOf
或者__proto__
为null
的时候才会终止查找。
上面这些步骤我们是看不到的,但这就是浏览器【查找】的属性,也是【搜索】的过程。这个【搜索的过程】,是连着由__proto__
组成的一个像链子一样的东西,浏览器跟随着这个链子走,我们就把这条链子就叫做【原型链】
共享原型链
现在我们有另一个对象var obj2 = { name: 'obj2' }
通过控制台打印我们会发现和我们的第一个是一样的,也有那么多的属性,这是什么意思呢?
但当我们改写了obj2 的 某一个属性的时候,第一个也会改变!这样obj和obj2就是具有某些相同行为的对象。他们实质上是共享了同一个原型链。
差异化
如果我们想让obj和obj2做不一样的行为,该怎么做呢?
我们可以直接给他们不同的行为
var obj.toString = function(){
return '新的 toString的方法'
}